From: Michal 'vorner' Vaner Date: Thu, 4 Jul 2013 08:50:12 +0000 (+0200) Subject: [2861] Test the main thread part of callbacks X-Git-Tag: bind10-1.2.0beta1-release~343^2~7 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=6ad2bdd472dd5ef1156577667c09bc0bd90d3f39;p=thirdparty%2Fkea.git [2861] Test the main thread part of callbacks --- diff --git a/src/bin/auth/tests/datasrc_clients_mgr_unittest.cc b/src/bin/auth/tests/datasrc_clients_mgr_unittest.cc index c805cbbd2a..86d244354c 100644 --- a/src/bin/auth/tests/datasrc_clients_mgr_unittest.cc +++ b/src/bin/auth/tests/datasrc_clients_mgr_unittest.cc @@ -245,6 +245,47 @@ TEST(DataSrcClientsMgrTest, reload) { EXPECT_EQ(3, FakeDataSrcClientsBuilder::command_queue->size()); } +void +callback(bool* called, int *tag_target, int tag_value) { + *called = true; + *tag_target = tag_value; +} + +// Test we can wake up the main thread by writing to the file descriptor and +// that the callbacks are executed and removed when woken up. +TEST(DataSrcClientsMgrTest, wakeup) { + bool called = false; + int tag; + { + TestDataSrcClientsMgr mgr; + // There's some real file descriptor (or something that looks so) + ASSERT_GT(FakeDataSrcClientsBuilder::wakeup_fd, 0); + // Push a callback in and wake the manager + FakeDataSrcClientsBuilder::callback_queue-> + push_back(boost::bind(callback, &called, &tag, 1)); + write(FakeDataSrcClientsBuilder::wakeup_fd, "w", 1); + mgr.run_one(); + EXPECT_TRUE(called); + EXPECT_EQ(1, tag); + EXPECT_TRUE(FakeDataSrcClientsBuilder::callback_queue->empty()); + + called = false; + // If we wake up and don't push anything, it doesn't break. + write(FakeDataSrcClientsBuilder::wakeup_fd, "w", 1); + mgr.run_one(); + EXPECT_FALSE(called); + + // When we terminate, it should process whatever is left + // of the callbacks. So push and terminate (and don't directly + // wake). + FakeDataSrcClientsBuilder::callback_queue-> + push_back(boost::bind(callback, &called, &tag, 2)); + } + EXPECT_TRUE(called); + EXPECT_EQ(2, tag); + EXPECT_TRUE(FakeDataSrcClientsBuilder::callback_queue->empty()); +} + TEST(DataSrcClientsMgrTest, realThread) { // Using the non-test definition with a real thread. Just checking // no disruption happens. diff --git a/src/bin/auth/tests/test_datasrc_clients_mgr.cc b/src/bin/auth/tests/test_datasrc_clients_mgr.cc index e8363604a6..80bc97c346 100644 --- a/src/bin/auth/tests/test_datasrc_clients_mgr.cc +++ b/src/bin/auth/tests/test_datasrc_clients_mgr.cc @@ -26,7 +26,9 @@ namespace datasrc_clientmgr_internal { // Define static DataSrcClientsBuilder member variables. bool FakeDataSrcClientsBuilder::started = false; std::list* FakeDataSrcClientsBuilder::command_queue = NULL; +std::list* FakeDataSrcClientsBuilder::callback_queue = NULL; std::list FakeDataSrcClientsBuilder::command_queue_copy; +std::list FakeDataSrcClientsBuilder::callback_queue_copy; TestCondVar* FakeDataSrcClientsBuilder::cond = NULL; TestCondVar FakeDataSrcClientsBuilder::cond_copy; TestMutex* FakeDataSrcClientsBuilder::queue_mutex = NULL; @@ -38,6 +40,7 @@ bool FakeDataSrcClientsBuilder::thread_waited = false; FakeDataSrcClientsBuilder::ExceptionFromWait FakeDataSrcClientsBuilder::thread_throw_on_wait = FakeDataSrcClientsBuilder::NOTHROW; +int FakeDataSrcClientsBuilder::wakeup_fd = -1; template<> void @@ -73,6 +76,10 @@ TestDataSrcClientsMgrBase::cleanup() { FakeDataSrcClientsBuilder::cond_copy = cond_; FakeDataSrcClientsBuilder::cond = &FakeDataSrcClientsBuilder::cond_copy; + FakeDataSrcClientsBuilder::callback_queue_copy = + *FakeDataSrcClientsBuilder::callback_queue; + FakeDataSrcClientsBuilder::callback_queue = + &FakeDataSrcClientsBuilder::callback_queue_copy; } template<> diff --git a/src/bin/auth/tests/test_datasrc_clients_mgr.h b/src/bin/auth/tests/test_datasrc_clients_mgr.h index faf5112180..34097da39f 100644 --- a/src/bin/auth/tests/test_datasrc_clients_mgr.h +++ b/src/bin/auth/tests/test_datasrc_clients_mgr.h @@ -133,15 +133,18 @@ public: // true iff a builder has started. static bool started; - // These three correspond to the resource shared with the manager. + // These five correspond to the resource shared with the manager. // xxx_copy will be set in the manager's destructor to record the // final state of the manager. static std::list* command_queue; + static std::list* callback_queue; static TestCondVar* cond; static TestMutex* queue_mutex; + static int wakeup_fd; static isc::datasrc::ClientListMapPtr* clients_map; static TestMutex* map_mutex; static std::list command_queue_copy; + static std::list callback_queue_copy; static TestCondVar cond_copy; static TestMutex queue_mutex_copy; @@ -155,16 +158,18 @@ public: FakeDataSrcClientsBuilder( std::list* command_queue, - std::list*, + std::list* callback_queue, TestCondVar* cond, TestMutex* queue_mutex, isc::datasrc::ClientListMapPtr* clients_map, - TestMutex* map_mutex, int) + TestMutex* map_mutex, int wakeup_fd) { FakeDataSrcClientsBuilder::started = false; FakeDataSrcClientsBuilder::command_queue = command_queue; + FakeDataSrcClientsBuilder::callback_queue = callback_queue; FakeDataSrcClientsBuilder::cond = cond; FakeDataSrcClientsBuilder::queue_mutex = queue_mutex; + FakeDataSrcClientsBuilder::wakeup_fd = wakeup_fd; FakeDataSrcClientsBuilder::clients_map = clients_map; FakeDataSrcClientsBuilder::map_mutex = map_mutex; FakeDataSrcClientsBuilder::thread_waited = false;