void run_timed_wait_regular_test() { Baton<Atom> b; auto thr = DSched::thread([&] { // To wait forever we'd like to use time_point<Clock>::max, but // std::condition_variable does math to convert the timeout to // system_clock without handling overflow. auto farFuture = Clock::now() + std::chrono::hours(1000); bool rv = b.timed_wait(farFuture); if (!std::is_same<Atom<int>, DeterministicAtomic<int>>::value) { // DeterministicAtomic ignores actual times, so doesn't guarantee // a lack of timeout EXPECT_TRUE(rv); } }); if (!std::is_same<Atom<int>, DeterministicAtomic<int>>::value) { // If we are using std::atomic (or EmulatedFutexAtomic) then // a sleep here guarantees to a large extent that 'thr' will // execute wait before we post it, thus testing late delivery. For // DeterministicAtomic, we just rely on DeterministicSchedule to do // the scheduling. The test won't fail if we lose the race, we just // don't get coverage. std::this_thread::sleep_for(std::chrono::milliseconds(2)); } b.post(); DSched::join(thr); }
TEST_F(EventBaseThreadTest, example) { EventBaseThread ebt; Baton<> done; ebt.getEventBase()->runInEventBaseThread([&] { done.post(); }); ASSERT_TRUE(done.timed_wait(seconds(1))); }
TEST(Interrupt, withinTimedOut) { Promise<int> p; Baton<> done; p.setInterruptHandler([&](const exception_wrapper& /* e */) { done.post(); }); p.getFuture().within(std::chrono::milliseconds(1)); // Give it 100ms to time out and call the interrupt handler auto t = std::chrono::steady_clock::now() + std::chrono::milliseconds(100); EXPECT_TRUE(done.timed_wait(t)); }
void run_timed_wait_tmo_tests() { Baton<Atom> b; auto thr = DSched::thread([&]{ bool rv = b.timed_wait(Clock::now() + std::chrono::milliseconds(1)); // main thread is guaranteed to not post until timeout occurs EXPECT_FALSE(rv); }); DSched::join(thr); }
TEST_F(EventBaseThreadTest, self_move) { EventBaseThread ebt0; auto ebt = std::move(ebt0); EXPECT_NE(nullptr, ebt.getEventBase()); Baton<> done; ebt.getEventBase()->runInEventBaseThread([&] { done.post(); }); ASSERT_TRUE(done.timed_wait(seconds(1))); }
TEST_F(FilePollerTest, TestUpdateFileBackwards) { createFile(); Baton<> baton; bool updated = false; FilePoller poller(tmpFile, std::chrono::milliseconds(1)); poller.addCallback([&]() { updated = true; baton.post(); }); updateModifiedTime(tmpFile, false); ASSERT_TRUE(baton.timed_wait(std::chrono::seconds(5))); ASSERT_TRUE(updated); }
TEST_F(FilePollerTest, TestDeleteFile) { Baton<> baton; bool updated = false; createFile(); FilePoller poller(tmpFile, std::chrono::milliseconds(1)); poller.addCallback([&]() { updated = true; baton.post(); }); remove(tmpFile.c_str()); ASSERT_TRUE(baton.timed_wait(std::chrono::seconds(5))); ASSERT_TRUE(updated); }
TEST_F(ProcessTicketTest, TestUpdateTicketFile) { Baton<> baton; TLSTicketProcessor processor(ticketFile); bool updated = false; processor.addCallback([&](TLSTicketKeySeeds) { updated = true; baton.post(); }); CHECK(writeFile(validTicketData, ticketFile.c_str())); updateModifiedTime(ticketFile); baton.timed_wait(std::chrono::seconds(30)); ASSERT_TRUE(updated); }
TEST_F(EventBaseThreadTest, move) { auto ebt0 = EventBaseThread(); auto ebt1 = std::move(ebt0); auto ebt2 = std::move(ebt1); EXPECT_EQ(nullptr, ebt0.getEventBase()); EXPECT_EQ(nullptr, ebt1.getEventBase()); EXPECT_NE(nullptr, ebt2.getEventBase()); Baton<> done; ebt2.getEventBase()->runInEventBaseThread([&] { done.post(); }); ASSERT_TRUE(done.timed_wait(seconds(1))); }
TEST_F(EventBaseThreadTest, start_stop) { EventBaseThread ebt(false); for (size_t i = 0; i < 4; ++i) { EXPECT_EQ(nullptr, ebt.getEventBase()); ebt.start(); EXPECT_NE(nullptr, ebt.getEventBase()); Baton<> done; ebt.getEventBase()->runInEventBaseThread([&] { done.post(); }); ASSERT_TRUE(done.timed_wait(seconds(1))); EXPECT_NE(nullptr, ebt.getEventBase()); ebt.stop(); EXPECT_EQ(nullptr, ebt.getEventBase()); } }
void run_timed_wait_regular_test() { Baton<Atom> b; auto thr = DSched::thread([&] { bool rv = b.timed_wait( std::chrono::time_point<std::chrono::system_clock>::max()); if (std::is_same<Atom<int>, std::atomic<int>>::value) { // We can only ensure this for std::atomic EXPECT_TRUE(rv); } }); if (std::is_same<Atom<int>, std::atomic<int>>::value) { // If we are using std::atomic, then a sleep here guarantees to a large // extent that 'thr' will execute wait before we post it, thus testing // late delivery. For DeterministicAtomic, we just rely on // DeterministicSchedule to do the scheduling std::this_thread::sleep_for(std::chrono::milliseconds(2)); } b.post(); DSched::join(thr); }
void run_basic_timed_wait_tests() { Baton<Atom> b; b.post(); // tests if early delivery works fine EXPECT_TRUE(b.timed_wait(std::chrono::system_clock::now())); }