mirror of
https://github.com/XRPLF/rippled.git
synced 2025-12-06 17:27:55 +00:00
Format first-party source according to .clang-format
This commit is contained in:
committed by
manojsdoshi
parent
65dfc5d19e
commit
50760c6935
@@ -17,11 +17,11 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/core/ClosureCounter.h>
|
||||
#include <ripple/beast/unit_test.h>
|
||||
#include <test/jtx/Env.h>
|
||||
#include <ripple/core/ClosureCounter.h>
|
||||
#include <atomic>
|
||||
#include <chrono>
|
||||
#include <test/jtx/Env.h>
|
||||
#include <thread>
|
||||
|
||||
namespace ripple {
|
||||
@@ -32,77 +32,78 @@ namespace test {
|
||||
class ClosureCounter_test : public beast::unit_test::suite
|
||||
{
|
||||
// We're only using Env for its Journal.
|
||||
jtx::Env env {*this};
|
||||
beast::Journal j {env.app().journal ("ClosureCounter_test")};
|
||||
jtx::Env env{*this};
|
||||
beast::Journal j{env.app().journal("ClosureCounter_test")};
|
||||
|
||||
void testConstruction()
|
||||
void
|
||||
testConstruction()
|
||||
{
|
||||
// Build different kinds of ClosureCounters.
|
||||
{
|
||||
// Count closures that return void and take no arguments.
|
||||
ClosureCounter<void> voidCounter;
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
|
||||
int evidence = 0;
|
||||
// Make sure voidCounter.wrap works with an rvalue closure.
|
||||
auto wrapped = voidCounter.wrap ([&evidence] () { ++evidence; });
|
||||
BEAST_EXPECT (voidCounter.count() == 1);
|
||||
BEAST_EXPECT (evidence == 0);
|
||||
BEAST_EXPECT (wrapped);
|
||||
auto wrapped = voidCounter.wrap([&evidence]() { ++evidence; });
|
||||
BEAST_EXPECT(voidCounter.count() == 1);
|
||||
BEAST_EXPECT(evidence == 0);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
// wrapped() should be callable with no arguments.
|
||||
(*wrapped)();
|
||||
BEAST_EXPECT (evidence == 1);
|
||||
BEAST_EXPECT(evidence == 1);
|
||||
(*wrapped)();
|
||||
BEAST_EXPECT (evidence == 2);
|
||||
BEAST_EXPECT(evidence == 2);
|
||||
|
||||
// Destroying the contents of wrapped should decrement voidCounter.
|
||||
wrapped = boost::none;
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
}
|
||||
{
|
||||
// Count closures that return void and take one int argument.
|
||||
ClosureCounter<void, int> setCounter;
|
||||
BEAST_EXPECT (setCounter.count() == 0);
|
||||
BEAST_EXPECT(setCounter.count() == 0);
|
||||
|
||||
int evidence = 0;
|
||||
// Make sure setCounter.wrap works with a non-const lvalue closure.
|
||||
auto setInt = [&evidence] (int i) { evidence = i; };
|
||||
auto wrapped = setCounter.wrap (setInt);
|
||||
auto setInt = [&evidence](int i) { evidence = i; };
|
||||
auto wrapped = setCounter.wrap(setInt);
|
||||
|
||||
BEAST_EXPECT (setCounter.count() == 1);
|
||||
BEAST_EXPECT (evidence == 0);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(setCounter.count() == 1);
|
||||
BEAST_EXPECT(evidence == 0);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
// wrapped() should be callable with one integer argument.
|
||||
(*wrapped)(5);
|
||||
BEAST_EXPECT (evidence == 5);
|
||||
BEAST_EXPECT(evidence == 5);
|
||||
(*wrapped)(11);
|
||||
BEAST_EXPECT (evidence == 11);
|
||||
BEAST_EXPECT(evidence == 11);
|
||||
|
||||
// Destroying the contents of wrapped should decrement setCounter.
|
||||
wrapped = boost::none;
|
||||
BEAST_EXPECT (setCounter.count() == 0);
|
||||
BEAST_EXPECT(setCounter.count() == 0);
|
||||
}
|
||||
{
|
||||
// Count closures that return int and take two int arguments.
|
||||
ClosureCounter<int, int, int> sumCounter;
|
||||
BEAST_EXPECT (sumCounter.count() == 0);
|
||||
BEAST_EXPECT(sumCounter.count() == 0);
|
||||
|
||||
// Make sure sumCounter.wrap works with a const lvalue closure.
|
||||
auto const sum = [] (int ii, int jj) { return ii + jj; };
|
||||
auto wrapped = sumCounter.wrap (sum);
|
||||
auto const sum = [](int ii, int jj) { return ii + jj; };
|
||||
auto wrapped = sumCounter.wrap(sum);
|
||||
|
||||
BEAST_EXPECT (sumCounter.count() == 1);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(sumCounter.count() == 1);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
// wrapped() should be callable with two integers.
|
||||
BEAST_EXPECT ((*wrapped)(5, 2) == 7);
|
||||
BEAST_EXPECT ((*wrapped)(2, -8) == -6);
|
||||
BEAST_EXPECT((*wrapped)(5, 2) == 7);
|
||||
BEAST_EXPECT((*wrapped)(2, -8) == -6);
|
||||
|
||||
// Destroying the contents of wrapped should decrement sumCounter.
|
||||
wrapped = boost::none;
|
||||
BEAST_EXPECT (sumCounter.count() == 0);
|
||||
BEAST_EXPECT(sumCounter.count() == 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,204 +117,211 @@ class ClosureCounter_test : public beast::unit_test::suite
|
||||
|
||||
TrackedString() = delete;
|
||||
|
||||
explicit TrackedString(char const* rhs)
|
||||
: str (rhs) {}
|
||||
explicit TrackedString(char const* rhs) : str(rhs)
|
||||
{
|
||||
}
|
||||
|
||||
// Copy constructor
|
||||
TrackedString (TrackedString const& rhs)
|
||||
: copies (rhs.copies + 1)
|
||||
, moves (rhs.moves)
|
||||
, str (rhs.str) {}
|
||||
TrackedString(TrackedString const& rhs)
|
||||
: copies(rhs.copies + 1), moves(rhs.moves), str(rhs.str)
|
||||
{
|
||||
}
|
||||
|
||||
// Move constructor
|
||||
TrackedString (TrackedString&& rhs) noexcept
|
||||
: copies (rhs.copies)
|
||||
, moves (rhs.moves + 1)
|
||||
, str (std::move(rhs.str)) {}
|
||||
TrackedString(TrackedString&& rhs) noexcept
|
||||
: copies(rhs.copies), moves(rhs.moves + 1), str(std::move(rhs.str))
|
||||
{
|
||||
}
|
||||
|
||||
// Delete copy and move assignment.
|
||||
TrackedString& operator=(TrackedString const& rhs) = delete;
|
||||
TrackedString&
|
||||
operator=(TrackedString const& rhs) = delete;
|
||||
|
||||
// String concatenation
|
||||
TrackedString& operator+=(char const* rhs)
|
||||
TrackedString&
|
||||
operator+=(char const* rhs)
|
||||
{
|
||||
str += rhs;
|
||||
return *this;
|
||||
}
|
||||
|
||||
friend
|
||||
TrackedString operator+(TrackedString const& s, char const* rhs)
|
||||
friend TrackedString
|
||||
operator+(TrackedString const& s, char const* rhs)
|
||||
{
|
||||
TrackedString ret {s};
|
||||
TrackedString ret{s};
|
||||
ret.str += rhs;
|
||||
return ret;
|
||||
}
|
||||
};
|
||||
|
||||
void testArgs()
|
||||
void
|
||||
testArgs()
|
||||
{
|
||||
// Make sure a wrapped closure handles rvalue reference arguments
|
||||
// correctly.
|
||||
{
|
||||
// Pass by value.
|
||||
ClosureCounter<TrackedString, TrackedString> strCounter;
|
||||
BEAST_EXPECT (strCounter.count() == 0);
|
||||
BEAST_EXPECT(strCounter.count() == 0);
|
||||
|
||||
auto wrapped = strCounter.wrap (
|
||||
[] (TrackedString in) { return in += "!"; });
|
||||
auto wrapped =
|
||||
strCounter.wrap([](TrackedString in) { return in += "!"; });
|
||||
|
||||
BEAST_EXPECT (strCounter.count() == 1);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(strCounter.count() == 1);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
TrackedString const strValue ("value");
|
||||
TrackedString const strValue("value");
|
||||
TrackedString const result = (*wrapped)(strValue);
|
||||
BEAST_EXPECT (result.copies == 2);
|
||||
BEAST_EXPECT (result.moves == 1);
|
||||
BEAST_EXPECT (result.str == "value!");
|
||||
BEAST_EXPECT (strValue.str.size() == 5);
|
||||
BEAST_EXPECT(result.copies == 2);
|
||||
BEAST_EXPECT(result.moves == 1);
|
||||
BEAST_EXPECT(result.str == "value!");
|
||||
BEAST_EXPECT(strValue.str.size() == 5);
|
||||
}
|
||||
{
|
||||
// Use a const lvalue argument.
|
||||
ClosureCounter<TrackedString, TrackedString const&> strCounter;
|
||||
BEAST_EXPECT (strCounter.count() == 0);
|
||||
BEAST_EXPECT(strCounter.count() == 0);
|
||||
|
||||
auto wrapped = strCounter.wrap (
|
||||
[] (TrackedString const& in) { return in + "!"; });
|
||||
auto wrapped = strCounter.wrap(
|
||||
[](TrackedString const& in) { return in + "!"; });
|
||||
|
||||
BEAST_EXPECT (strCounter.count() == 1);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(strCounter.count() == 1);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
TrackedString const strConstLValue ("const lvalue");
|
||||
TrackedString const strConstLValue("const lvalue");
|
||||
TrackedString const result = (*wrapped)(strConstLValue);
|
||||
BEAST_EXPECT (result.copies == 1);
|
||||
BEAST_EXPECT(result.copies == 1);
|
||||
// BEAST_EXPECT (result.moves == ?); // moves VS == 1, gcc == 0
|
||||
BEAST_EXPECT (result.str == "const lvalue!");
|
||||
BEAST_EXPECT (strConstLValue.str.size() == 12);
|
||||
BEAST_EXPECT(result.str == "const lvalue!");
|
||||
BEAST_EXPECT(strConstLValue.str.size() == 12);
|
||||
}
|
||||
{
|
||||
// Use a non-const lvalue argument.
|
||||
ClosureCounter<TrackedString, TrackedString&> strCounter;
|
||||
BEAST_EXPECT (strCounter.count() == 0);
|
||||
BEAST_EXPECT(strCounter.count() == 0);
|
||||
|
||||
auto wrapped = strCounter.wrap (
|
||||
[] (TrackedString& in) { return in += "!"; });
|
||||
auto wrapped =
|
||||
strCounter.wrap([](TrackedString& in) { return in += "!"; });
|
||||
|
||||
BEAST_EXPECT (strCounter.count() == 1);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(strCounter.count() == 1);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
TrackedString strLValue ("lvalue");
|
||||
TrackedString strLValue("lvalue");
|
||||
TrackedString const result = (*wrapped)(strLValue);
|
||||
BEAST_EXPECT (result.copies == 1);
|
||||
BEAST_EXPECT (result.moves == 0);
|
||||
BEAST_EXPECT (result.str == "lvalue!");
|
||||
BEAST_EXPECT (strLValue.str == result.str);
|
||||
BEAST_EXPECT(result.copies == 1);
|
||||
BEAST_EXPECT(result.moves == 0);
|
||||
BEAST_EXPECT(result.str == "lvalue!");
|
||||
BEAST_EXPECT(strLValue.str == result.str);
|
||||
}
|
||||
{
|
||||
// Use an rvalue argument.
|
||||
ClosureCounter<TrackedString, TrackedString&&> strCounter;
|
||||
BEAST_EXPECT (strCounter.count() == 0);
|
||||
BEAST_EXPECT(strCounter.count() == 0);
|
||||
|
||||
auto wrapped = strCounter.wrap (
|
||||
[] (TrackedString&& in) {
|
||||
// Note that none of the compilers noticed that in was
|
||||
// leaving scope. So, without intervention, they would
|
||||
// do a copy for the return (June 2017). An explicit
|
||||
// std::move() was required.
|
||||
return std::move(in += "!");
|
||||
});
|
||||
auto wrapped = strCounter.wrap([](TrackedString&& in) {
|
||||
// Note that none of the compilers noticed that in was
|
||||
// leaving scope. So, without intervention, they would
|
||||
// do a copy for the return (June 2017). An explicit
|
||||
// std::move() was required.
|
||||
return std::move(in += "!");
|
||||
});
|
||||
|
||||
BEAST_EXPECT (strCounter.count() == 1);
|
||||
BEAST_EXPECT (wrapped);
|
||||
BEAST_EXPECT(strCounter.count() == 1);
|
||||
BEAST_EXPECT(wrapped);
|
||||
|
||||
// Make the string big enough to (probably) avoid the small string
|
||||
// optimization.
|
||||
TrackedString strRValue ("rvalue abcdefghijklmnopqrstuvwxyz");
|
||||
TrackedString strRValue("rvalue abcdefghijklmnopqrstuvwxyz");
|
||||
TrackedString const result = (*wrapped)(std::move(strRValue));
|
||||
BEAST_EXPECT (result.copies == 0);
|
||||
BEAST_EXPECT (result.moves == 1);
|
||||
BEAST_EXPECT (result.str == "rvalue abcdefghijklmnopqrstuvwxyz!");
|
||||
BEAST_EXPECT (strRValue.str.size() == 0);
|
||||
BEAST_EXPECT(result.copies == 0);
|
||||
BEAST_EXPECT(result.moves == 1);
|
||||
BEAST_EXPECT(result.str == "rvalue abcdefghijklmnopqrstuvwxyz!");
|
||||
BEAST_EXPECT(strRValue.str.size() == 0);
|
||||
}
|
||||
}
|
||||
|
||||
void testWrap()
|
||||
void
|
||||
testWrap()
|
||||
{
|
||||
// Verify reference counting.
|
||||
ClosureCounter<void> voidCounter;
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
{
|
||||
auto wrapped1 = voidCounter.wrap ([] () {});
|
||||
BEAST_EXPECT (voidCounter.count() == 1);
|
||||
auto wrapped1 = voidCounter.wrap([]() {});
|
||||
BEAST_EXPECT(voidCounter.count() == 1);
|
||||
{
|
||||
// Copy should increase reference count.
|
||||
auto wrapped2 (wrapped1);
|
||||
BEAST_EXPECT (voidCounter.count() == 2);
|
||||
auto wrapped2(wrapped1);
|
||||
BEAST_EXPECT(voidCounter.count() == 2);
|
||||
{
|
||||
// Move should increase reference count.
|
||||
auto wrapped3 (std::move(wrapped2));
|
||||
BEAST_EXPECT (voidCounter.count() == 3);
|
||||
auto wrapped3(std::move(wrapped2));
|
||||
BEAST_EXPECT(voidCounter.count() == 3);
|
||||
{
|
||||
// An additional closure also increases count.
|
||||
auto wrapped4 = voidCounter.wrap ([] () {});
|
||||
BEAST_EXPECT (voidCounter.count() == 4);
|
||||
auto wrapped4 = voidCounter.wrap([]() {});
|
||||
BEAST_EXPECT(voidCounter.count() == 4);
|
||||
}
|
||||
BEAST_EXPECT (voidCounter.count() == 3);
|
||||
BEAST_EXPECT(voidCounter.count() == 3);
|
||||
}
|
||||
BEAST_EXPECT (voidCounter.count() == 2);
|
||||
BEAST_EXPECT(voidCounter.count() == 2);
|
||||
}
|
||||
BEAST_EXPECT (voidCounter.count() == 1);
|
||||
BEAST_EXPECT(voidCounter.count() == 1);
|
||||
}
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
|
||||
// Join with 0 count should not stall.
|
||||
using namespace std::chrono_literals;
|
||||
voidCounter.join("testWrap", 1ms, j);
|
||||
|
||||
// Wrapping a closure after join() should return boost::none.
|
||||
BEAST_EXPECT (voidCounter.wrap ([] () {}) == boost::none);
|
||||
BEAST_EXPECT(voidCounter.wrap([]() {}) == boost::none);
|
||||
}
|
||||
|
||||
void testWaitOnJoin()
|
||||
void
|
||||
testWaitOnJoin()
|
||||
{
|
||||
// Verify reference counting.
|
||||
ClosureCounter<void> voidCounter;
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
|
||||
auto wrapped = (voidCounter.wrap ([] () {}));
|
||||
BEAST_EXPECT (voidCounter.count() == 1);
|
||||
auto wrapped = (voidCounter.wrap([]() {}));
|
||||
BEAST_EXPECT(voidCounter.count() == 1);
|
||||
|
||||
// Calling join() now should stall, so do it on a different thread.
|
||||
std::atomic<bool> threadExited {false};
|
||||
std::thread localThread ([&voidCounter, &threadExited, this] ()
|
||||
{
|
||||
std::atomic<bool> threadExited{false};
|
||||
std::thread localThread([&voidCounter, &threadExited, this]() {
|
||||
// Should stall after calling join.
|
||||
using namespace std::chrono_literals;
|
||||
voidCounter.join("testWaitOnJoin", 1ms, j);
|
||||
threadExited.store (true);
|
||||
threadExited.store(true);
|
||||
});
|
||||
|
||||
// Wait for the thread to call voidCounter.join().
|
||||
while (! voidCounter.joined());
|
||||
while (!voidCounter.joined())
|
||||
;
|
||||
|
||||
// The thread should still be active after waiting 5 milliseconds.
|
||||
// This is not a guarantee that join() stalled the thread, but it
|
||||
// improves confidence.
|
||||
using namespace std::chrono_literals;
|
||||
std::this_thread::sleep_for (5ms);
|
||||
BEAST_EXPECT (threadExited == false);
|
||||
std::this_thread::sleep_for(5ms);
|
||||
BEAST_EXPECT(threadExited == false);
|
||||
|
||||
// Destroy the contents of wrapped and expect the thread to exit
|
||||
// (asynchronously).
|
||||
wrapped = boost::none;
|
||||
BEAST_EXPECT (voidCounter.count() == 0);
|
||||
BEAST_EXPECT(voidCounter.count() == 0);
|
||||
|
||||
// Wait for the thread to exit.
|
||||
while (threadExited == false);
|
||||
while (threadExited == false)
|
||||
;
|
||||
localThread.join();
|
||||
}
|
||||
|
||||
public:
|
||||
void run() override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
testConstruction();
|
||||
testArgs();
|
||||
@@ -324,5 +332,5 @@ public:
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(ClosureCounter, core, ripple);
|
||||
|
||||
} // test
|
||||
} // ripple
|
||||
} // namespace test
|
||||
} // namespace ripple
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -18,10 +18,10 @@
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <test/jtx.h>
|
||||
#include <chrono>
|
||||
#include <condition_variable>
|
||||
#include <mutex>
|
||||
#include <test/jtx.h>
|
||||
|
||||
namespace ripple {
|
||||
namespace test {
|
||||
@@ -44,7 +44,7 @@ public:
|
||||
wait_for(std::chrono::duration<Rep, Period> const& rel_time)
|
||||
{
|
||||
std::unique_lock<std::mutex> lk(mutex_);
|
||||
auto b = cv_.wait_for(lk, rel_time, [=]{ return signaled_; });
|
||||
auto b = cv_.wait_for(lk, rel_time, [=] { return signaled_; });
|
||||
signaled_ = false;
|
||||
return b;
|
||||
}
|
||||
@@ -68,14 +68,12 @@ public:
|
||||
jq.setThreadCount(0, false);
|
||||
gate g1, g2;
|
||||
std::shared_ptr<JobQueue::Coro> c;
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test",
|
||||
[&](auto const& cr)
|
||||
{
|
||||
c = cr;
|
||||
g1.signal();
|
||||
c->yield();
|
||||
g2.signal();
|
||||
});
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test", [&](auto const& cr) {
|
||||
c = cr;
|
||||
g1.signal();
|
||||
c->yield();
|
||||
g2.signal();
|
||||
});
|
||||
BEAST_EXPECT(g1.wait_for(5s));
|
||||
c->join();
|
||||
c->post();
|
||||
@@ -91,13 +89,11 @@ public:
|
||||
auto& jq = env.app().getJobQueue();
|
||||
jq.setThreadCount(0, false);
|
||||
gate g;
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test",
|
||||
[&](auto const& c)
|
||||
{
|
||||
c->post();
|
||||
c->yield();
|
||||
g.signal();
|
||||
});
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test", [&](auto const& c) {
|
||||
c->post();
|
||||
c->yield();
|
||||
g.signal();
|
||||
});
|
||||
BEAST_EXPECT(g.wait_for(5s));
|
||||
}
|
||||
|
||||
@@ -116,55 +112,49 @@ public:
|
||||
BEAST_EXPECT(*lv == -1);
|
||||
|
||||
gate g;
|
||||
jq.addJob(jtCLIENT, "LocalValue-Test",
|
||||
[&](auto const& job)
|
||||
{
|
||||
this->BEAST_EXPECT(*lv == -1);
|
||||
*lv = -2;
|
||||
this->BEAST_EXPECT(*lv == -2);
|
||||
g.signal();
|
||||
});
|
||||
jq.addJob(jtCLIENT, "LocalValue-Test", [&](auto const& job) {
|
||||
this->BEAST_EXPECT(*lv == -1);
|
||||
*lv = -2;
|
||||
this->BEAST_EXPECT(*lv == -2);
|
||||
g.signal();
|
||||
});
|
||||
BEAST_EXPECT(g.wait_for(5s));
|
||||
BEAST_EXPECT(*lv == -1);
|
||||
|
||||
for(int i = 0; i < N; ++i)
|
||||
for (int i = 0; i < N; ++i)
|
||||
{
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test",
|
||||
[&, id = i](auto const& c)
|
||||
{
|
||||
a[id] = c;
|
||||
g.signal();
|
||||
c->yield();
|
||||
jq.postCoro(jtCLIENT, "Coroutine-Test", [&, id = i](auto const& c) {
|
||||
a[id] = c;
|
||||
g.signal();
|
||||
c->yield();
|
||||
|
||||
this->BEAST_EXPECT(*lv == -1);
|
||||
*lv = id;
|
||||
this->BEAST_EXPECT(*lv == id);
|
||||
g.signal();
|
||||
c->yield();
|
||||
this->BEAST_EXPECT(*lv == -1);
|
||||
*lv = id;
|
||||
this->BEAST_EXPECT(*lv == id);
|
||||
g.signal();
|
||||
c->yield();
|
||||
|
||||
this->BEAST_EXPECT(*lv == id);
|
||||
});
|
||||
this->BEAST_EXPECT(*lv == id);
|
||||
});
|
||||
BEAST_EXPECT(g.wait_for(5s));
|
||||
a[i]->join();
|
||||
}
|
||||
for(auto const& c : a)
|
||||
for (auto const& c : a)
|
||||
{
|
||||
c->post();
|
||||
BEAST_EXPECT(g.wait_for(5s));
|
||||
c->join();
|
||||
}
|
||||
for(auto const& c : a)
|
||||
for (auto const& c : a)
|
||||
{
|
||||
c->post();
|
||||
c->join();
|
||||
}
|
||||
|
||||
jq.addJob(jtCLIENT, "LocalValue-Test",
|
||||
[&](auto const& job)
|
||||
{
|
||||
this->BEAST_EXPECT(*lv == -2);
|
||||
g.signal();
|
||||
});
|
||||
jq.addJob(jtCLIENT, "LocalValue-Test", [&](auto const& job) {
|
||||
this->BEAST_EXPECT(*lv == -2);
|
||||
g.signal();
|
||||
});
|
||||
BEAST_EXPECT(g.wait_for(5s));
|
||||
BEAST_EXPECT(*lv == -1);
|
||||
}
|
||||
@@ -178,7 +168,7 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(Coroutine,core,ripple);
|
||||
BEAST_DEFINE_TESTSUITE(Coroutine, core, ripple);
|
||||
|
||||
} // test
|
||||
} // ripple
|
||||
} // namespace test
|
||||
} // namespace ripple
|
||||
|
||||
@@ -17,12 +17,12 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <test/jtx/Env.h>
|
||||
#include <ripple/beast/utility/temp_dir.h>
|
||||
#include <ripple/crypto/csprng.h>
|
||||
#include <boost/filesystem.hpp>
|
||||
#include <fstream>
|
||||
#include <streambuf>
|
||||
#include <test/jtx/Env.h>
|
||||
|
||||
namespace ripple {
|
||||
|
||||
@@ -31,7 +31,7 @@ class CryptoPRNG_test : public beast::unit_test::suite
|
||||
void
|
||||
testGetValues()
|
||||
{
|
||||
testcase ("Get Values");
|
||||
testcase("Get Values");
|
||||
try
|
||||
{
|
||||
auto& engine = crypto_prng();
|
||||
@@ -39,23 +39,24 @@ class CryptoPRNG_test : public beast::unit_test::suite
|
||||
BEAST_EXPECT(rand_val >= engine.min());
|
||||
BEAST_EXPECT(rand_val <= engine.max());
|
||||
|
||||
uint16_t twoByte {0};
|
||||
uint16_t twoByte{0};
|
||||
engine(&twoByte, sizeof(uint16_t));
|
||||
pass();
|
||||
}
|
||||
catch(std::exception&)
|
||||
catch (std::exception&)
|
||||
{
|
||||
fail();
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
void run () override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
testGetValues();
|
||||
}
|
||||
};
|
||||
|
||||
BEAST_DEFINE_TESTSUITE (CryptoPRNG, core, ripple);
|
||||
BEAST_DEFINE_TESTSUITE(CryptoPRNG, core, ripple);
|
||||
|
||||
} // ripple
|
||||
} // namespace ripple
|
||||
|
||||
@@ -17,8 +17,8 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <ripple/beast/unit_test.h>
|
||||
#include <ripple/core/JobQueue.h>
|
||||
#include <test/jtx/Env.h>
|
||||
|
||||
namespace ripple {
|
||||
@@ -28,26 +28,30 @@ namespace test {
|
||||
|
||||
class JobQueue_test : public beast::unit_test::suite
|
||||
{
|
||||
void testAddJob()
|
||||
void
|
||||
testAddJob()
|
||||
{
|
||||
jtx::Env env {*this};
|
||||
jtx::Env env{*this};
|
||||
|
||||
JobQueue& jQueue = env.app().getJobQueue();
|
||||
{
|
||||
// addJob() should run the Job (and return true).
|
||||
std::atomic<bool> jobRan {false};
|
||||
BEAST_EXPECT (jQueue.addJob (jtCLIENT, "JobAddTest1",
|
||||
[&jobRan] (Job&) { jobRan = true; }) == true);
|
||||
std::atomic<bool> jobRan{false};
|
||||
BEAST_EXPECT(
|
||||
jQueue.addJob(jtCLIENT, "JobAddTest1", [&jobRan](Job&) {
|
||||
jobRan = true;
|
||||
}) == true);
|
||||
|
||||
// Wait for the Job to run.
|
||||
while (jobRan == false);
|
||||
while (jobRan == false)
|
||||
;
|
||||
}
|
||||
{
|
||||
// If the JobQueue's JobCounter is join()ed we should no
|
||||
// longer be able to add Jobs (and calling addJob() should
|
||||
// return false).
|
||||
using namespace std::chrono_literals;
|
||||
beast::Journal j {env.app().journal ("JobQueue_test")};
|
||||
beast::Journal j{env.app().journal("JobQueue_test")};
|
||||
JobCounter& jCounter = jQueue.jobCounter();
|
||||
jCounter.join("JobQueue_test", 1s, j);
|
||||
|
||||
@@ -55,55 +59,63 @@ class JobQueue_test : public beast::unit_test::suite
|
||||
// unprotected variable on the stack should be completely safe.
|
||||
// Not recommended for the faint of heart...
|
||||
bool unprotected;
|
||||
BEAST_EXPECT (jQueue.addJob (jtCLIENT, "JobAddTest2",
|
||||
[&unprotected] (Job&) { unprotected = false; }) == false);
|
||||
BEAST_EXPECT(
|
||||
jQueue.addJob(jtCLIENT, "JobAddTest2", [&unprotected](Job&) {
|
||||
unprotected = false;
|
||||
}) == false);
|
||||
}
|
||||
}
|
||||
|
||||
void testPostCoro()
|
||||
void
|
||||
testPostCoro()
|
||||
{
|
||||
jtx::Env env {*this};
|
||||
jtx::Env env{*this};
|
||||
|
||||
JobQueue& jQueue = env.app().getJobQueue();
|
||||
{
|
||||
// Test repeated post()s until the Coro completes.
|
||||
std::atomic<int> yieldCount {0};
|
||||
auto const coro = jQueue.postCoro (jtCLIENT, "PostCoroTest1",
|
||||
[&yieldCount] (std::shared_ptr<JobQueue::Coro> const& coroCopy)
|
||||
{
|
||||
std::atomic<int> yieldCount{0};
|
||||
auto const coro = jQueue.postCoro(
|
||||
jtCLIENT,
|
||||
"PostCoroTest1",
|
||||
[&yieldCount](std::shared_ptr<JobQueue::Coro> const& coroCopy) {
|
||||
while (++yieldCount < 4)
|
||||
coroCopy->yield();
|
||||
});
|
||||
BEAST_EXPECT (coro != nullptr);
|
||||
BEAST_EXPECT(coro != nullptr);
|
||||
|
||||
// Wait for the Job to run and yield.
|
||||
while (yieldCount == 0);
|
||||
while (yieldCount == 0)
|
||||
;
|
||||
|
||||
// Now re-post until the Coro says it is done.
|
||||
int old = yieldCount;
|
||||
while (coro->runnable())
|
||||
{
|
||||
BEAST_EXPECT (coro->post());
|
||||
while (old == yieldCount) { }
|
||||
BEAST_EXPECT(coro->post());
|
||||
while (old == yieldCount)
|
||||
{
|
||||
}
|
||||
coro->join();
|
||||
BEAST_EXPECT (++old == yieldCount);
|
||||
BEAST_EXPECT(++old == yieldCount);
|
||||
}
|
||||
BEAST_EXPECT (yieldCount == 4);
|
||||
BEAST_EXPECT(yieldCount == 4);
|
||||
}
|
||||
{
|
||||
// Test repeated resume()s until the Coro completes.
|
||||
int yieldCount {0};
|
||||
auto const coro = jQueue.postCoro (jtCLIENT, "PostCoroTest2",
|
||||
[&yieldCount] (std::shared_ptr<JobQueue::Coro> const& coroCopy)
|
||||
{
|
||||
int yieldCount{0};
|
||||
auto const coro = jQueue.postCoro(
|
||||
jtCLIENT,
|
||||
"PostCoroTest2",
|
||||
[&yieldCount](std::shared_ptr<JobQueue::Coro> const& coroCopy) {
|
||||
while (++yieldCount < 4)
|
||||
coroCopy->yield();
|
||||
});
|
||||
if (! coro)
|
||||
if (!coro)
|
||||
{
|
||||
// There's no good reason we should not get a Coro, but we
|
||||
// can't continue without one.
|
||||
BEAST_EXPECT (false);
|
||||
BEAST_EXPECT(false);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -114,17 +126,17 @@ class JobQueue_test : public beast::unit_test::suite
|
||||
int old = yieldCount;
|
||||
while (coro->runnable())
|
||||
{
|
||||
coro->resume(); // Resume runs synchronously on this thread.
|
||||
BEAST_EXPECT (++old == yieldCount);
|
||||
coro->resume(); // Resume runs synchronously on this thread.
|
||||
BEAST_EXPECT(++old == yieldCount);
|
||||
}
|
||||
BEAST_EXPECT (yieldCount == 4);
|
||||
BEAST_EXPECT(yieldCount == 4);
|
||||
}
|
||||
{
|
||||
// If the JobQueue's JobCounter is join()ed we should no
|
||||
// longer be able to add a Coro (and calling postCoro() should
|
||||
// return false).
|
||||
using namespace std::chrono_literals;
|
||||
beast::Journal j {env.app().journal ("JobQueue_test")};
|
||||
beast::Journal j{env.app().journal("JobQueue_test")};
|
||||
JobCounter& jCounter = jQueue.jobCounter();
|
||||
jCounter.join("JobQueue_test", 1s, j);
|
||||
|
||||
@@ -132,15 +144,19 @@ class JobQueue_test : public beast::unit_test::suite
|
||||
// unprotected variable on the stack should be completely safe.
|
||||
// Not recommended for the faint of heart...
|
||||
bool unprotected;
|
||||
auto const coro = jQueue.postCoro (jtCLIENT, "PostCoroTest3",
|
||||
[&unprotected] (std::shared_ptr<JobQueue::Coro> const&)
|
||||
{ unprotected = false; });
|
||||
BEAST_EXPECT (coro == nullptr);
|
||||
auto const coro = jQueue.postCoro(
|
||||
jtCLIENT,
|
||||
"PostCoroTest3",
|
||||
[&unprotected](std::shared_ptr<JobQueue::Coro> const&) {
|
||||
unprotected = false;
|
||||
});
|
||||
BEAST_EXPECT(coro == nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
void run() override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
testAddJob();
|
||||
testPostCoro();
|
||||
@@ -149,5 +165,5 @@ public:
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(JobQueue, core, ripple);
|
||||
|
||||
} // test
|
||||
} // ripple
|
||||
} // namespace test
|
||||
} // namespace ripple
|
||||
|
||||
@@ -17,85 +17,90 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
|
||||
#include <ripple/basics/BasicConfig.h>
|
||||
#include <ripple/basics/contract.h>
|
||||
#include <ripple/core/ConfigSections.h>
|
||||
#include <ripple/core/SociDB.h>
|
||||
#include <ripple/basics/contract.h>
|
||||
#include <test/jtx/TestSuite.h>
|
||||
#include <ripple/basics/BasicConfig.h>
|
||||
#include <boost/filesystem.hpp>
|
||||
#include <boost/algorithm/string.hpp>
|
||||
#include <boost/filesystem.hpp>
|
||||
#include <test/jtx/TestSuite.h>
|
||||
|
||||
namespace ripple {
|
||||
class SociDB_test final : public TestSuite
|
||||
{
|
||||
private:
|
||||
static void setupSQLiteConfig (BasicConfig& config,
|
||||
boost::filesystem::path const& dbPath)
|
||||
static void
|
||||
setupSQLiteConfig(
|
||||
BasicConfig& config,
|
||||
boost::filesystem::path const& dbPath)
|
||||
{
|
||||
config.overwrite ("sqdb", "backend", "sqlite");
|
||||
auto value = dbPath.string ();
|
||||
if (!value.empty ())
|
||||
config.legacy ("database_path", value);
|
||||
config.overwrite("sqdb", "backend", "sqlite");
|
||||
auto value = dbPath.string();
|
||||
if (!value.empty())
|
||||
config.legacy("database_path", value);
|
||||
}
|
||||
|
||||
static void cleanupDatabaseDir (boost::filesystem::path const& dbPath)
|
||||
static void
|
||||
cleanupDatabaseDir(boost::filesystem::path const& dbPath)
|
||||
{
|
||||
using namespace boost::filesystem;
|
||||
if (!exists (dbPath) || !is_directory (dbPath) || !is_empty (dbPath))
|
||||
if (!exists(dbPath) || !is_directory(dbPath) || !is_empty(dbPath))
|
||||
return;
|
||||
remove (dbPath);
|
||||
remove(dbPath);
|
||||
}
|
||||
|
||||
static void setupDatabaseDir (boost::filesystem::path const& dbPath)
|
||||
static void
|
||||
setupDatabaseDir(boost::filesystem::path const& dbPath)
|
||||
{
|
||||
using namespace boost::filesystem;
|
||||
if (!exists (dbPath))
|
||||
if (!exists(dbPath))
|
||||
{
|
||||
create_directory (dbPath);
|
||||
create_directory(dbPath);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!is_directory (dbPath))
|
||||
if (!is_directory(dbPath))
|
||||
{
|
||||
// someone created a file where we want to put out directory
|
||||
Throw<std::runtime_error> (
|
||||
"Cannot create directory: " + dbPath.string ());
|
||||
Throw<std::runtime_error>(
|
||||
"Cannot create directory: " + dbPath.string());
|
||||
}
|
||||
}
|
||||
static boost::filesystem::path getDatabasePath ()
|
||||
static boost::filesystem::path
|
||||
getDatabasePath()
|
||||
{
|
||||
return boost::filesystem::current_path () / "socidb_test_databases";
|
||||
return boost::filesystem::current_path() / "socidb_test_databases";
|
||||
}
|
||||
|
||||
public:
|
||||
SociDB_test ()
|
||||
SociDB_test()
|
||||
{
|
||||
try
|
||||
{
|
||||
setupDatabaseDir (getDatabasePath ());
|
||||
setupDatabaseDir(getDatabasePath());
|
||||
}
|
||||
catch (std::exception const&)
|
||||
{
|
||||
}
|
||||
}
|
||||
~SociDB_test ()
|
||||
~SociDB_test()
|
||||
{
|
||||
try
|
||||
{
|
||||
cleanupDatabaseDir (getDatabasePath ());
|
||||
cleanupDatabaseDir(getDatabasePath());
|
||||
}
|
||||
catch (std::exception const&)
|
||||
{
|
||||
}
|
||||
}
|
||||
void testSQLiteFileNames ()
|
||||
void
|
||||
testSQLiteFileNames()
|
||||
{
|
||||
// confirm that files are given the correct exensions
|
||||
testcase ("sqliteFileNames");
|
||||
testcase("sqliteFileNames");
|
||||
BasicConfig c;
|
||||
setupSQLiteConfig (c, getDatabasePath ());
|
||||
std::vector<std::pair<std::string, std::string>> const d (
|
||||
setupSQLiteConfig(c, getDatabasePath());
|
||||
std::vector<std::pair<std::string, std::string>> const d(
|
||||
{{"peerfinder", ".sqlite"},
|
||||
{"state", ".db"},
|
||||
{"random", ".db"},
|
||||
@@ -103,45 +108,46 @@ public:
|
||||
|
||||
for (auto const& i : d)
|
||||
{
|
||||
SociConfig sc (c, i.first);
|
||||
BEAST_EXPECT(boost::ends_with (sc.connectionString (),
|
||||
i.first + i.second));
|
||||
SociConfig sc(c, i.first);
|
||||
BEAST_EXPECT(
|
||||
boost::ends_with(sc.connectionString(), i.first + i.second));
|
||||
}
|
||||
}
|
||||
void testSQLiteSession ()
|
||||
void
|
||||
testSQLiteSession()
|
||||
{
|
||||
testcase ("open");
|
||||
testcase("open");
|
||||
BasicConfig c;
|
||||
setupSQLiteConfig (c, getDatabasePath ());
|
||||
SociConfig sc (c, "SociTestDB");
|
||||
std::vector<std::string> const stringData (
|
||||
setupSQLiteConfig(c, getDatabasePath());
|
||||
SociConfig sc(c, "SociTestDB");
|
||||
std::vector<std::string> const stringData(
|
||||
{"String1", "String2", "String3"});
|
||||
std::vector<int> const intData ({1, 2, 3});
|
||||
auto checkValues = [this, &stringData, &intData](soci::session& s)
|
||||
{
|
||||
std::vector<int> const intData({1, 2, 3});
|
||||
auto checkValues = [this, &stringData, &intData](soci::session& s) {
|
||||
// Check values in db
|
||||
std::vector<std::string> stringResult (20 * stringData.size ());
|
||||
std::vector<int> intResult (20 * intData.size ());
|
||||
std::vector<std::string> stringResult(20 * stringData.size());
|
||||
std::vector<int> intResult(20 * intData.size());
|
||||
s << "SELECT StringData, IntData FROM SociTestTable;",
|
||||
soci::into (stringResult), soci::into (intResult);
|
||||
BEAST_EXPECT(stringResult.size () == stringData.size () &&
|
||||
intResult.size () == intData.size ());
|
||||
for (int i = 0; i < stringResult.size (); ++i)
|
||||
soci::into(stringResult), soci::into(intResult);
|
||||
BEAST_EXPECT(
|
||||
stringResult.size() == stringData.size() &&
|
||||
intResult.size() == intData.size());
|
||||
for (int i = 0; i < stringResult.size(); ++i)
|
||||
{
|
||||
auto si = std::distance (stringData.begin (),
|
||||
std::find (stringData.begin (),
|
||||
stringData.end (),
|
||||
stringResult[i]));
|
||||
auto ii = std::distance (
|
||||
intData.begin (),
|
||||
std::find (intData.begin (), intData.end (), intResult[i]));
|
||||
BEAST_EXPECT(si == ii && si < stringResult.size ());
|
||||
auto si = std::distance(
|
||||
stringData.begin(),
|
||||
std::find(
|
||||
stringData.begin(), stringData.end(), stringResult[i]));
|
||||
auto ii = std::distance(
|
||||
intData.begin(),
|
||||
std::find(intData.begin(), intData.end(), intResult[i]));
|
||||
BEAST_EXPECT(si == ii && si < stringResult.size());
|
||||
}
|
||||
};
|
||||
|
||||
{
|
||||
soci::session s;
|
||||
sc.open (s);
|
||||
sc.open(s);
|
||||
s << "CREATE TABLE IF NOT EXISTS SociTestTable ("
|
||||
" Key INTEGER PRIMARY KEY,"
|
||||
" StringData TEXT,"
|
||||
@@ -150,40 +156,41 @@ public:
|
||||
|
||||
s << "INSERT INTO SociTestTable (StringData, IntData) VALUES "
|
||||
"(:stringData, :intData);",
|
||||
soci::use (stringData), soci::use (intData);
|
||||
checkValues (s);
|
||||
soci::use(stringData), soci::use(intData);
|
||||
checkValues(s);
|
||||
}
|
||||
{
|
||||
// Check values in db after session was closed
|
||||
soci::session s;
|
||||
sc.open (s);
|
||||
checkValues (s);
|
||||
sc.open(s);
|
||||
checkValues(s);
|
||||
}
|
||||
{
|
||||
namespace bfs = boost::filesystem;
|
||||
// Remove the database
|
||||
bfs::path dbPath (sc.connectionString ());
|
||||
if (bfs::is_regular_file (dbPath))
|
||||
bfs::remove (dbPath);
|
||||
bfs::path dbPath(sc.connectionString());
|
||||
if (bfs::is_regular_file(dbPath))
|
||||
bfs::remove(dbPath);
|
||||
}
|
||||
}
|
||||
|
||||
void testSQLiteSelect ()
|
||||
void
|
||||
testSQLiteSelect()
|
||||
{
|
||||
testcase ("select");
|
||||
testcase("select");
|
||||
BasicConfig c;
|
||||
setupSQLiteConfig (c, getDatabasePath ());
|
||||
SociConfig sc (c, "SociTestDB");
|
||||
std::vector<std::uint64_t> const ubid (
|
||||
{(std::uint64_t)std::numeric_limits<std::int64_t>::max (), 20, 30});
|
||||
std::vector<std::int64_t> const bid ({-10, -20, -30});
|
||||
std::vector<std::uint32_t> const uid (
|
||||
{std::numeric_limits<std::uint32_t>::max (), 2, 3});
|
||||
std::vector<std::int32_t> const id ({-1, -2, -3});
|
||||
setupSQLiteConfig(c, getDatabasePath());
|
||||
SociConfig sc(c, "SociTestDB");
|
||||
std::vector<std::uint64_t> const ubid(
|
||||
{(std::uint64_t)std::numeric_limits<std::int64_t>::max(), 20, 30});
|
||||
std::vector<std::int64_t> const bid({-10, -20, -30});
|
||||
std::vector<std::uint32_t> const uid(
|
||||
{std::numeric_limits<std::uint32_t>::max(), 2, 3});
|
||||
std::vector<std::int32_t> const id({-1, -2, -3});
|
||||
|
||||
{
|
||||
soci::session s;
|
||||
sc.open (s);
|
||||
sc.open(s);
|
||||
|
||||
s << "DROP TABLE IF EXISTS STT;";
|
||||
|
||||
@@ -196,8 +203,7 @@ public:
|
||||
|
||||
s << "INSERT INTO STT (I, UI, BI, UBI) VALUES "
|
||||
"(:id, :idu, :bid, :bidu);",
|
||||
soci::use (id), soci::use (uid), soci::use (bid),
|
||||
soci::use (ubid);
|
||||
soci::use(id), soci::use(uid), soci::use(bid), soci::use(ubid);
|
||||
|
||||
try
|
||||
{
|
||||
@@ -205,14 +211,15 @@ public:
|
||||
std::uint32_t uig = 0;
|
||||
std::int64_t big = 0;
|
||||
std::uint64_t ubig = 0;
|
||||
s << "SELECT I, UI, BI, UBI from STT;", soci::into (ig),
|
||||
soci::into (uig), soci::into (big), soci::into (ubig);
|
||||
BEAST_EXPECT(ig == id[0] && uig == uid[0] && big == bid[0] &&
|
||||
ubig == ubid[0]);
|
||||
s << "SELECT I, UI, BI, UBI from STT;", soci::into(ig),
|
||||
soci::into(uig), soci::into(big), soci::into(ubig);
|
||||
BEAST_EXPECT(
|
||||
ig == id[0] && uig == uid[0] && big == bid[0] &&
|
||||
ubig == ubid[0]);
|
||||
}
|
||||
catch (std::exception&)
|
||||
{
|
||||
fail ();
|
||||
fail();
|
||||
}
|
||||
try
|
||||
{
|
||||
@@ -220,18 +227,20 @@ public:
|
||||
boost::optional<std::uint32_t> uig;
|
||||
boost::optional<std::int64_t> big;
|
||||
boost::optional<std::uint64_t> ubig;
|
||||
s << "SELECT I, UI, BI, UBI from STT;", soci::into (ig),
|
||||
soci::into (uig), soci::into (big), soci::into (ubig);
|
||||
BEAST_EXPECT(*ig == id[0] && *uig == uid[0] && *big == bid[0] &&
|
||||
*ubig == ubid[0]);
|
||||
s << "SELECT I, UI, BI, UBI from STT;", soci::into(ig),
|
||||
soci::into(uig), soci::into(big), soci::into(ubig);
|
||||
BEAST_EXPECT(
|
||||
*ig == id[0] && *uig == uid[0] && *big == bid[0] &&
|
||||
*ubig == ubid[0]);
|
||||
}
|
||||
catch (std::exception&)
|
||||
{
|
||||
fail ();
|
||||
fail();
|
||||
}
|
||||
// There are too many issues when working with soci::row and boost::tuple. DO NOT USE
|
||||
// soci row! I had a set of workarounds to make soci row less error prone, I'm keeping
|
||||
// these tests in case I try to add soci::row and boost::tuple back into soci.
|
||||
// There are too many issues when working with soci::row and
|
||||
// boost::tuple. DO NOT USE soci row! I had a set of workarounds to
|
||||
// make soci row less error prone, I'm keeping these tests in case I
|
||||
// try to add soci::row and boost::tuple back into soci.
|
||||
#if 0
|
||||
try
|
||||
{
|
||||
@@ -290,20 +299,21 @@ public:
|
||||
{
|
||||
namespace bfs = boost::filesystem;
|
||||
// Remove the database
|
||||
bfs::path dbPath (sc.connectionString ());
|
||||
if (bfs::is_regular_file (dbPath))
|
||||
bfs::remove (dbPath);
|
||||
bfs::path dbPath(sc.connectionString());
|
||||
if (bfs::is_regular_file(dbPath))
|
||||
bfs::remove(dbPath);
|
||||
}
|
||||
}
|
||||
void testSQLiteDeleteWithSubselect()
|
||||
void
|
||||
testSQLiteDeleteWithSubselect()
|
||||
{
|
||||
testcase ("deleteWithSubselect");
|
||||
testcase("deleteWithSubselect");
|
||||
BasicConfig c;
|
||||
setupSQLiteConfig (c, getDatabasePath ());
|
||||
SociConfig sc (c, "SociTestDB");
|
||||
setupSQLiteConfig(c, getDatabasePath());
|
||||
SociConfig sc(c, "SociTestDB");
|
||||
{
|
||||
soci::session s;
|
||||
sc.open (s);
|
||||
sc.open(s);
|
||||
const char* dbInit[] = {
|
||||
"BEGIN TRANSACTION;",
|
||||
"CREATE TABLE Ledgers ( \
|
||||
@@ -317,7 +327,7 @@ public:
|
||||
s << dbInit[i];
|
||||
}
|
||||
char lh[65];
|
||||
memset (lh, 'a', 64);
|
||||
memset(lh, 'a', 64);
|
||||
lh[64] = '\0';
|
||||
int toIncIndex = 63;
|
||||
int const numRows = 16;
|
||||
@@ -335,31 +345,33 @@ public:
|
||||
}
|
||||
s << "INSERT INTO Ledgers (LedgerHash, LedgerSeq) VALUES "
|
||||
"(:lh, :li);",
|
||||
soci::use (ledgerHashes), soci::use (ledgerIndexes);
|
||||
soci::use(ledgerHashes), soci::use(ledgerIndexes);
|
||||
|
||||
std::vector<int> ledgersLS (numRows * 2);
|
||||
s << "SELECT LedgerSeq FROM Ledgers;", soci::into (ledgersLS);
|
||||
BEAST_EXPECT(ledgersLS.size () == numRows);
|
||||
std::vector<int> ledgersLS(numRows * 2);
|
||||
s << "SELECT LedgerSeq FROM Ledgers;", soci::into(ledgersLS);
|
||||
BEAST_EXPECT(ledgersLS.size() == numRows);
|
||||
}
|
||||
namespace bfs = boost::filesystem;
|
||||
// Remove the database
|
||||
bfs::path dbPath (sc.connectionString ());
|
||||
if (bfs::is_regular_file (dbPath))
|
||||
bfs::remove (dbPath);
|
||||
bfs::path dbPath(sc.connectionString());
|
||||
if (bfs::is_regular_file(dbPath))
|
||||
bfs::remove(dbPath);
|
||||
}
|
||||
void testSQLite ()
|
||||
void
|
||||
testSQLite()
|
||||
{
|
||||
testSQLiteFileNames ();
|
||||
testSQLiteSession ();
|
||||
testSQLiteSelect ();
|
||||
testSQLiteFileNames();
|
||||
testSQLiteSession();
|
||||
testSQLiteSelect();
|
||||
testSQLiteDeleteWithSubselect();
|
||||
}
|
||||
void run () override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
testSQLite ();
|
||||
testSQLite();
|
||||
}
|
||||
};
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(SociDB,core,ripple);
|
||||
BEAST_DEFINE_TESTSUITE(SociDB, core, ripple);
|
||||
|
||||
} // ripple
|
||||
} // namespace ripple
|
||||
|
||||
@@ -17,168 +17,190 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/core/Stoppable.h>
|
||||
#include <ripple/beast/unit_test.h>
|
||||
#include <ripple/core/Stoppable.h>
|
||||
#include <test/unit_test/SuiteJournal.h>
|
||||
#include <thread>
|
||||
|
||||
namespace ripple {
|
||||
namespace test {
|
||||
|
||||
class Stoppable_test
|
||||
: public beast::unit_test::suite
|
||||
class Stoppable_test : public beast::unit_test::suite
|
||||
{
|
||||
/*
|
||||
R
|
||||
/ | \
|
||||
/ | \
|
||||
A B C
|
||||
/ | \ /\ |
|
||||
D E F G H I
|
||||
|
|
||||
J
|
||||
*/
|
||||
/*
|
||||
R
|
||||
/ | \
|
||||
/ | \
|
||||
A B C
|
||||
/ | \ /\ |
|
||||
D E F G H I
|
||||
|
|
||||
J
|
||||
*/
|
||||
unsigned count = 0;
|
||||
|
||||
class D
|
||||
: public Stoppable
|
||||
class D : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
D(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("D", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("D", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 9, "D::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 9, "D::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 0, "D::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 11, "D::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 2, "D::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 2, "D::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class J
|
||||
: public Stoppable
|
||||
class J : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
J(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("J", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("J", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 7, "J::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 7, "J::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 1, "J::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 10, "J::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 4, "J::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 4, "J::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class E
|
||||
: public Stoppable
|
||||
class E : public Stoppable
|
||||
{
|
||||
J j_;
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
E(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("E", parent)
|
||||
, j_(*this, test)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("E", parent), j_(*this, test), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 8, "E::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 8, "E::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 2, "E::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 9, "E::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 3, "E::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 3, "E::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class F
|
||||
: public Stoppable
|
||||
class F : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
F(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("F", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("F", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 6, "F::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 6, "F::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 3, "F::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 8, "F::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 5, "F::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 5, "F::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class A
|
||||
: public Stoppable
|
||||
class A : public Stoppable
|
||||
{
|
||||
enum {running, please_stop, stopping, stopped};
|
||||
enum { running, please_stop, stopping, stopped };
|
||||
D d_;
|
||||
E e_;
|
||||
F f_;
|
||||
Stoppable_test& test_;
|
||||
std::atomic<int> stop_;
|
||||
|
||||
public:
|
||||
A(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("A", parent)
|
||||
@@ -187,214 +209,252 @@ class Stoppable_test
|
||||
, f_(*this, test)
|
||||
, test_(test)
|
||||
, stop_(running)
|
||||
{}
|
||||
{
|
||||
}
|
||||
~A() override
|
||||
{
|
||||
while (stop_ != stopped)
|
||||
;
|
||||
}
|
||||
|
||||
void run()
|
||||
void
|
||||
run()
|
||||
{
|
||||
while (stop_ == running)
|
||||
;
|
||||
stop_ = stopping;
|
||||
}
|
||||
|
||||
void onPrepare() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(++test_.count == 10, "A::onPrepare called out of order");
|
||||
test_.expect(
|
||||
++test_.count == 10, "A::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 4, "A::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 7, "A::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
stop_ = please_stop;
|
||||
while (stop_ != stopping)
|
||||
;
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 1, "A::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 1, "A::onChildrenStopped called out of order");
|
||||
stop_ = stopped;
|
||||
}
|
||||
};
|
||||
|
||||
class G
|
||||
: public Stoppable
|
||||
class G : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
G(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("G", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("G", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 4, "G::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 4, "G::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 5, "G::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 6, "G::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 7, "G::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 7, "G::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class H
|
||||
: public Stoppable
|
||||
class H : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
H(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("H", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("H", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 3, "H::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 3, "H::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 6, "H::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 5, "H::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 8, "H::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 8, "H::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class B
|
||||
: public Stoppable
|
||||
class B : public Stoppable
|
||||
{
|
||||
G g_;
|
||||
H h_;
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
B(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("B", parent)
|
||||
, g_(*this, test)
|
||||
, h_(*this, test)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
{
|
||||
test_.expect(++test_.count == 5, "B::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 5, "B::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 7, "B::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 4, "B::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 6, "B::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 6, "B::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class I
|
||||
: public Stoppable
|
||||
class I : public Stoppable
|
||||
{
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
I(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("I", parent)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("I", parent), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 1, "I::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 1, "I::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 8, "I::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 3, "I::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 10, "I::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 10,
|
||||
"I::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class C
|
||||
: public Stoppable
|
||||
class C : public Stoppable
|
||||
{
|
||||
I i_;
|
||||
Stoppable_test& test_;
|
||||
|
||||
public:
|
||||
C(Stoppable& parent, Stoppable_test& test)
|
||||
: Stoppable("C", parent)
|
||||
, i_(*this, test)
|
||||
, test_(test)
|
||||
{}
|
||||
|
||||
void onPrepare() override
|
||||
: Stoppable("C", parent), i_(*this, test), test_(test)
|
||||
{
|
||||
test_.expect(++test_.count == 2, "C::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(
|
||||
++test_.count == 2, "C::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 9, "C::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 2, "C::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 9, "C::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 9, "C::onChildrenStopped called out of order");
|
||||
}
|
||||
};
|
||||
|
||||
class Root
|
||||
: public RootStoppable
|
||||
class Root : public RootStoppable
|
||||
{
|
||||
std::thread a_;
|
||||
B b_;
|
||||
@@ -410,47 +470,60 @@ class Stoppable_test
|
||||
, c_(*this, test)
|
||||
, test_(test)
|
||||
, journal_("Stoppable_test", test)
|
||||
{}
|
||||
{
|
||||
}
|
||||
|
||||
void run()
|
||||
void
|
||||
run()
|
||||
{
|
||||
prepare();
|
||||
start();
|
||||
stop (journal_);
|
||||
stop(journal_);
|
||||
}
|
||||
|
||||
void onPrepare() override
|
||||
void
|
||||
onPrepare() override
|
||||
{
|
||||
test_.expect(++test_.count == 11, "Root::onPrepare called out of order");
|
||||
test_.expect(
|
||||
++test_.count == 11, "Root::onPrepare called out of order");
|
||||
}
|
||||
|
||||
void onStart() override
|
||||
void
|
||||
onStart() override
|
||||
{
|
||||
test_.expect(--test_.count == 10, "Root::onStart called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 10, "Root::onStart called out of order");
|
||||
}
|
||||
|
||||
void onStop() override
|
||||
void
|
||||
onStop() override
|
||||
{
|
||||
test_.expect(++test_.count == 1, "Root::onStop called out of order");
|
||||
test_.expect(
|
||||
++test_.count == 1, "Root::onStop called out of order");
|
||||
}
|
||||
|
||||
void onChildrenStopped() override
|
||||
void
|
||||
onChildrenStopped() override
|
||||
{
|
||||
a_.join();
|
||||
Stoppable::stopped();
|
||||
test_.expect(--test_.count == 0, "Root::onChildrenStopped called out of order");
|
||||
test_.expect(
|
||||
--test_.count == 0,
|
||||
"Root::onChildrenStopped called out of order");
|
||||
}
|
||||
|
||||
void secondStop()
|
||||
void
|
||||
secondStop()
|
||||
{
|
||||
// Calling stop() a second time should have no negative
|
||||
// consequences.
|
||||
stop (journal_);
|
||||
stop(journal_);
|
||||
}
|
||||
};
|
||||
|
||||
public:
|
||||
void run() override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
{
|
||||
Root rt(*this);
|
||||
@@ -461,7 +534,7 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(Stoppable,core,ripple);
|
||||
BEAST_DEFINE_TESTSUITE(Stoppable, core, ripple);
|
||||
|
||||
}
|
||||
}
|
||||
} // namespace test
|
||||
} // namespace ripple
|
||||
|
||||
@@ -17,10 +17,10 @@ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#include <ripple/core/impl/Workers.h>
|
||||
#include <ripple/beast/unit_test.h>
|
||||
#include <ripple/basics/PerfLog.h>
|
||||
#include <ripple/beast/unit_test.h>
|
||||
#include <ripple/core/JobTypes.h>
|
||||
#include <ripple/core/impl/Workers.h>
|
||||
#include <ripple/json/json_value.h>
|
||||
#include <chrono>
|
||||
#include <condition_variable>
|
||||
@@ -37,49 +37,67 @@ namespace ripple {
|
||||
|
||||
namespace perf {
|
||||
|
||||
class PerfLogTest
|
||||
: public PerfLog
|
||||
class PerfLogTest : public PerfLog
|
||||
{
|
||||
void rpcStart(std::string const &method, std::uint64_t requestId) override
|
||||
{}
|
||||
void
|
||||
rpcStart(std::string const& method, std::uint64_t requestId) override
|
||||
{
|
||||
}
|
||||
|
||||
void rpcFinish(std::string const &method, std::uint64_t requestId) override
|
||||
{}
|
||||
void
|
||||
rpcFinish(std::string const& method, std::uint64_t requestId) override
|
||||
{
|
||||
}
|
||||
|
||||
void rpcError(std::string const &method, std::uint64_t dur) override
|
||||
{}
|
||||
void
|
||||
rpcError(std::string const& method, std::uint64_t dur) override
|
||||
{
|
||||
}
|
||||
|
||||
void jobQueue(JobType const type) override
|
||||
{}
|
||||
void
|
||||
jobQueue(JobType const type) override
|
||||
{
|
||||
}
|
||||
|
||||
void jobStart(JobType const type,
|
||||
void
|
||||
jobStart(
|
||||
JobType const type,
|
||||
std::chrono::microseconds dur,
|
||||
std::chrono::time_point<std::chrono::steady_clock> startTime,
|
||||
int instance) override
|
||||
{}
|
||||
{
|
||||
}
|
||||
|
||||
void jobFinish(JobType const type, std::chrono::microseconds dur,
|
||||
int instance) override
|
||||
{}
|
||||
void
|
||||
jobFinish(JobType const type, std::chrono::microseconds dur, int instance)
|
||||
override
|
||||
{
|
||||
}
|
||||
|
||||
Json::Value countersJson() const override
|
||||
Json::Value
|
||||
countersJson() const override
|
||||
{
|
||||
return Json::Value();
|
||||
}
|
||||
|
||||
Json::Value currentJson() const override
|
||||
Json::Value
|
||||
currentJson() const override
|
||||
{
|
||||
return Json::Value();
|
||||
}
|
||||
|
||||
void resizeJobs(int const resize) override
|
||||
{}
|
||||
void
|
||||
resizeJobs(int const resize) override
|
||||
{
|
||||
}
|
||||
|
||||
void rotate() override
|
||||
{}
|
||||
void
|
||||
rotate() override
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
} // perf
|
||||
} // namespace perf
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
@@ -88,7 +106,8 @@ class Workers_test : public beast::unit_test::suite
|
||||
public:
|
||||
struct TestCallback : Workers::Callback
|
||||
{
|
||||
void processTask(int instance) override
|
||||
void
|
||||
processTask(int instance) override
|
||||
{
|
||||
std::lock_guard lk{mut};
|
||||
if (--count == 0)
|
||||
@@ -96,14 +115,16 @@ public:
|
||||
}
|
||||
|
||||
std::condition_variable cv;
|
||||
std::mutex mut;
|
||||
int count = 0;
|
||||
std::mutex mut;
|
||||
int count = 0;
|
||||
};
|
||||
|
||||
void testThreads(int const tc1, int const tc2, int const tc3)
|
||||
void
|
||||
testThreads(int const tc1, int const tc2, int const tc3)
|
||||
{
|
||||
testcase("threadCounts: " + std::to_string(tc1) +
|
||||
" -> " + std::to_string(tc2) + " -> " + std::to_string(tc3));
|
||||
testcase(
|
||||
"threadCounts: " + std::to_string(tc1) + " -> " +
|
||||
std::to_string(tc2) + " -> " + std::to_string(tc3));
|
||||
|
||||
TestCallback cb;
|
||||
std::unique_ptr<perf::PerfLog> perfLog =
|
||||
@@ -112,8 +133,7 @@ public:
|
||||
Workers w(cb, perfLog.get(), "Test", tc1);
|
||||
BEAST_EXPECT(w.getNumberOfThreads() == tc1);
|
||||
|
||||
auto testForThreadCount = [this, &cb, &w] (int const threadCount)
|
||||
{
|
||||
auto testForThreadCount = [this, &cb, &w](int const threadCount) {
|
||||
// Prepare the callback.
|
||||
cb.count = threadCount;
|
||||
|
||||
@@ -128,25 +148,27 @@ public:
|
||||
//
|
||||
using namespace std::chrono_literals;
|
||||
std::unique_lock<std::mutex> lk{cb.mut};
|
||||
bool const signaled = cb.cv.wait_for(lk, 10s, [&cb]{return cb.count == 0;});
|
||||
bool const signaled =
|
||||
cb.cv.wait_for(lk, 10s, [&cb] { return cb.count == 0; });
|
||||
BEAST_EXPECT(signaled);
|
||||
BEAST_EXPECT(cb.count == 0);
|
||||
};
|
||||
testForThreadCount (tc1);
|
||||
testForThreadCount (tc2);
|
||||
testForThreadCount (tc3);
|
||||
testForThreadCount(tc1);
|
||||
testForThreadCount(tc2);
|
||||
testForThreadCount(tc3);
|
||||
w.pauseAllThreadsAndWait();
|
||||
|
||||
// We had better finished all our work!
|
||||
BEAST_EXPECT(cb.count == 0);
|
||||
}
|
||||
|
||||
void run() override
|
||||
void
|
||||
run() override
|
||||
{
|
||||
testThreads( 0, 0, 0);
|
||||
testThreads( 1, 0, 1);
|
||||
testThreads( 2, 1, 2);
|
||||
testThreads( 4, 3, 5);
|
||||
testThreads(0, 0, 0);
|
||||
testThreads(1, 0, 1);
|
||||
testThreads(2, 1, 2);
|
||||
testThreads(4, 3, 5);
|
||||
testThreads(16, 4, 15);
|
||||
testThreads(64, 3, 65);
|
||||
}
|
||||
@@ -154,4 +176,4 @@ public:
|
||||
|
||||
BEAST_DEFINE_TESTSUITE(Workers, core, ripple);
|
||||
|
||||
}
|
||||
} // namespace ripple
|
||||
|
||||
Reference in New Issue
Block a user