diff options
author | Chanho Park <chanho61.park@samsung.com> | 2014-12-11 18:55:56 +0900 |
---|---|---|
committer | Chanho Park <chanho61.park@samsung.com> | 2014-12-11 18:55:56 +0900 |
commit | 08c1e93fa36a49f49325a07fe91ff92c964c2b6c (patch) | |
tree | 7a7053ceb8874b28ec4b868d4c49b500008a102e /boost/interprocess/sync/spin/condition.hpp | |
parent | bb4dd8289b351fae6b55e303f189127a394a1edd (diff) | |
download | boost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.tar.gz boost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.tar.bz2 boost-08c1e93fa36a49f49325a07fe91ff92c964c2b6c.zip |
Imported Upstream version 1.57.0upstream/1.57.0
Diffstat (limited to 'boost/interprocess/sync/spin/condition.hpp')
-rw-r--r-- | boost/interprocess/sync/spin/condition.hpp | 43 |
1 files changed, 24 insertions, 19 deletions
diff --git a/boost/interprocess/sync/spin/condition.hpp b/boost/interprocess/sync/spin/condition.hpp index 55dd79b406..e587c32c9b 100644 --- a/boost/interprocess/sync/spin/condition.hpp +++ b/boost/interprocess/sync/spin/condition.hpp @@ -1,6 +1,6 @@ ////////////////////////////////////////////////////////////////////////////// // -// (C) Copyright Ion Gaztanaga 2005-2011. Distributed under the Boost +// (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost // Software License, Version 1.0. (See accompanying file // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) // @@ -11,6 +11,10 @@ #ifndef BOOST_INTERPROCESS_DETAIL_SPIN_CONDITION_HPP #define BOOST_INTERPROCESS_DETAIL_SPIN_CONDITION_HPP +#if defined(_MSC_VER) +# pragma once +#endif + #include <boost/interprocess/detail/config_begin.hpp> #include <boost/interprocess/detail/workaround.hpp> #include <boost/interprocess/sync/spin/mutex.hpp> @@ -19,7 +23,8 @@ #include <boost/interprocess/sync/scoped_lock.hpp> #include <boost/interprocess/exceptions.hpp> #include <boost/interprocess/detail/os_thread_functions.hpp> -#include <boost/move/move.hpp> +#include <boost/interprocess/sync/spin/wait.hpp> +#include <boost/move/utility_core.hpp> #include <boost/cstdint.hpp> namespace boost { @@ -40,24 +45,26 @@ class spin_condition template <typename L> bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time) { + if (!lock) + throw lock_exception(); + //Handle infinity absolute time here to avoid complications in do_timed_wait if(abs_time == boost::posix_time::pos_infin){ this->wait(lock); return true; } - if (!lock) - throw lock_exception(); return this->do_timed_wait(abs_time, *lock.mutex()); } template <typename L, typename Pr> bool timed_wait(L& lock, const boost::posix_time::ptime &abs_time, Pr pred) { + if (!lock) + throw lock_exception(); + //Handle infinity absolute time here to avoid complications in do_timed_wait if(abs_time == boost::posix_time::pos_infin){ this->wait(lock, pred); return true; } - if (!lock) - throw lock_exception(); while (!pred()){ if (!this->do_timed_wait(abs_time, *lock.mutex())) return pred(); @@ -110,8 +117,10 @@ inline spin_condition::spin_condition() } inline spin_condition::~spin_condition() -{ - //Trivial destructor +{ + //Notify all waiting threads + //to allow POSIX semantics on condition destruction + this->notify_all(); } inline void spin_condition::notify_one() @@ -140,15 +149,10 @@ inline void spin_condition::notify(boost::uint32_t command) } //Notify that all threads should execute wait logic + spin_wait swait; while(SLEEP != atomic_cas32(const_cast<boost::uint32_t*>(&m_command), command, SLEEP)){ - thread_yield(); + swait.yield(); } -/* - //Wait until the threads are woken - while(SLEEP != atomic_cas32(const_cast<boost::uint32_t*>(&m_command), 0)){ - thread_yield(); - } -*/ //The enter mutex will rest locked until the last waiting thread unlocks it } @@ -171,7 +175,7 @@ inline bool spin_condition::do_timed_wait(bool tout_enabled, InterprocessMutex &mut) { boost::posix_time::ptime now = microsec_clock::universal_time(); - + if(tout_enabled){ if(now >= abs_time) return false; } @@ -205,14 +209,15 @@ inline bool spin_condition::do_timed_wait(bool tout_enabled, //By default, we suppose that no timeout has happened bool timed_out = false, unlock_enter_mut= false; - + //Loop until a notification indicates that the thread should //exit or timeout occurs while(1){ //The thread sleeps/spins until a spin_condition commands a notification //Notification occurred, we will lock the checking mutex so that + spin_wait swait; while(atomic_read32(&m_command) == SLEEP){ - thread_yield(); + swait.yield(); //Check for timeout if(tout_enabled){ @@ -253,7 +258,7 @@ inline bool spin_condition::do_timed_wait(bool tout_enabled, continue; } else if(result == NOTIFY_ONE){ - //If it was a NOTIFY_ONE command, only this thread should + //If it was a NOTIFY_ONE command, only this thread should //exit. This thread has atomically marked command as sleep before //so no other thread will exit. //Decrement wait count. |