]> granicus.if.org Git - icinga2/commitdiff
Bugfix: Unlock thread mutex while waiting for events.
authorGunnar Beutner <gunnar.beutner@netways.de>
Sat, 16 Feb 2013 06:27:45 +0000 (07:27 +0100)
committerGunnar Beutner <gunnar.beutner@netways.de>
Sat, 16 Feb 2013 06:27:45 +0000 (07:27 +0100)
lib/base/application.cpp
lib/base/eventqueue.cpp
lib/base/eventqueue.h
lib/base/scriptinterpreter.cpp
lib/base/scriptinterpreter.h

index b9e944f3b0f39f801fbf08a3f986b557cd2a9009..531a8168de19b6412947a251bcf9953a61da5fbf 100644 (file)
@@ -124,7 +124,7 @@ bool Application::ProcessEvents(void)
        if (m_ShuttingDown)
                return false;
 
-       GetEQ().ProcessEvents(boost::posix_time::milliseconds(sleep * 1000));
+       GetEQ().ProcessEvents(m_Mutex, boost::posix_time::milliseconds(sleep * 1000));
 
        DynamicObject::FlushTx();
 
index 2b68a784d94f572910e9666c1edbdd767afd6a7d..a236e1cf1f0cd96619d02fe68080c7e03d66a472 100644 (file)
@@ -46,24 +46,33 @@ void EventQueue::Stop(void)
  * Waits for events using the specified timeout value and processes
  * them.
  *
+ * @param mtx The mutex that should be unlocked while waiting. Caller
+ *           must have this mutex locked.
  * @param timeout The wait timeout.
  * @returns false if the queue has been stopped, true otherwise.
  */
-bool EventQueue::ProcessEvents(millisec timeout)
+bool EventQueue::ProcessEvents(boost::mutex& mtx, millisec timeout)
 {
        vector<Callback> events;
 
+       mtx.unlock();
+
        {
                boost::mutex::scoped_lock lock(m_Mutex);
 
                while (m_Events.empty() && !m_Stopped) {
-                       if (!m_EventAvailable.timed_wait(lock, timeout))
+                       if (!m_EventAvailable.timed_wait(lock, timeout)) {
+                               mtx.lock();
+
                                return !m_Stopped;
+                       }
                }
 
                events.swap(m_Events);
        }
 
+       mtx.lock();
+
        BOOST_FOREACH(const Callback& ev, events) {
                double st = Utility::GetTime();
 
@@ -100,4 +109,3 @@ void EventQueue::Post(const EventQueue::Callback& callback)
                m_EventAvailable.notify_all();
        }
 }
-
index f5c0d70fe9a659b4624ee816f2313b93e5bfe675..422746482c6102919595e4bfb78584a140a7c229 100644 (file)
@@ -35,7 +35,7 @@ public:
 
        EventQueue(void);
 
-       bool ProcessEvents(millisec timeout = boost::posix_time::milliseconds(30000));
+       bool ProcessEvents(boost::mutex& mtx, millisec timeout = boost::posix_time::milliseconds(30000));
        void Post(const Callback& callback);
 
        void Stop(void);
@@ -43,6 +43,8 @@ public:
        boost::thread::id GetOwner(void) const;
        void SetOwner(boost::thread::id owner);
 
+       boost::mutex& GetMutex(void);
+
 private:
        boost::thread::id m_Owner;
 
index d336d92a3104fd9e1146e5ca319424453ec7fcd9..2810c0948dc229d23f9f79c2129986ab8bebbb48 100644 (file)
@@ -55,8 +55,12 @@ void ScriptInterpreter::ThreadWorkerProc(void)
 {
        m_EQ.SetOwner(boost::this_thread::get_id());
 
-       while (m_EQ.ProcessEvents())
-               ; /* empty loop */
+       {
+               boost::mutex::scoped_lock lock(m_Mutex);
+
+               while (m_EQ.ProcessEvents(m_Mutex))
+                       ; /* empty loop */
+       }
 }
 
 void ScriptInterpreter::ScriptFunctionThunk(const ScriptTask::Ptr& task,
index d687c4fc55c24ae9e9864c63489877f4507e4ea0..0ac0cdb58fa2df5c58b7d082a7687785ae33ba51 100644 (file)
@@ -49,6 +49,7 @@ protected:
        void UnsubscribeFunction(const String& name);
 
 private:
+       boost::mutex m_Mutex;
        EventQueue m_EQ;
        set<String> m_SubscribedFunctions;
        boost::thread m_Thread;