diff DEPENDENCIES/generic/include/boost/interprocess/sync/spin/mutex.hpp @ 16:2665513ce2d3

Add boost headers
author Chris Cannam
date Tue, 05 Aug 2014 11:11:38 +0100
parents
children c530137014c0
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/DEPENDENCIES/generic/include/boost/interprocess/sync/spin/mutex.hpp	Tue Aug 05 11:11:38 2014 +0100
@@ -0,0 +1,117 @@
+//////////////////////////////////////////////////////////////////////////////
+//
+// (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)
+//
+// See http://www.boost.org/libs/interprocess for documentation.
+//
+//////////////////////////////////////////////////////////////////////////////
+
+#ifndef BOOST_INTERPROCESS_DETAIL_SPIN_MUTEX_HPP
+#define BOOST_INTERPROCESS_DETAIL_SPIN_MUTEX_HPP
+
+#if (defined _MSC_VER) && (_MSC_VER >= 1200)
+#  pragma once
+#endif
+
+#include <boost/interprocess/detail/config_begin.hpp>
+#include <boost/interprocess/detail/workaround.hpp>
+#include <boost/interprocess/detail/posix_time_types_wrk.hpp>
+#include <boost/assert.hpp>
+#include <boost/interprocess/detail/atomic.hpp>
+#include <boost/cstdint.hpp>
+#include <boost/interprocess/detail/os_thread_functions.hpp>
+#include <boost/interprocess/sync/spin/wait.hpp>
+
+namespace boost {
+namespace interprocess {
+namespace ipcdetail {
+
+class spin_mutex
+{
+   spin_mutex(const spin_mutex &);
+   spin_mutex &operator=(const spin_mutex &);
+   public:
+
+   spin_mutex();
+   ~spin_mutex();
+
+   void lock();
+   bool try_lock();
+   bool timed_lock(const boost::posix_time::ptime &abs_time);
+   void unlock();
+   void take_ownership(){};
+   private:
+   volatile boost::uint32_t m_s;
+};
+
+inline spin_mutex::spin_mutex()
+   : m_s(0)
+{
+   //Note that this class is initialized to zero.
+   //So zeroed memory can be interpreted as an
+   //initialized mutex
+}
+
+inline spin_mutex::~spin_mutex()
+{
+   //Trivial destructor
+}
+
+inline void spin_mutex::lock(void)
+{
+   spin_wait swait;
+   do{
+      boost::uint32_t prev_s = ipcdetail::atomic_cas32(const_cast<boost::uint32_t*>(&m_s), 1, 0);
+
+      if (m_s == 1 && prev_s == 0){
+            break;
+      }
+      // relinquish current timeslice
+      swait.yield();
+   }while (true);
+}
+
+inline bool spin_mutex::try_lock(void)
+{
+   boost::uint32_t prev_s = ipcdetail::atomic_cas32(const_cast<boost::uint32_t*>(&m_s), 1, 0);
+   return m_s == 1 && prev_s == 0;
+}
+
+inline bool spin_mutex::timed_lock(const boost::posix_time::ptime &abs_time)
+{
+   if(abs_time == boost::posix_time::pos_infin){
+      this->lock();
+      return true;
+   }
+   //Obtain current count and target time
+   boost::posix_time::ptime now = microsec_clock::universal_time();
+
+   spin_wait swait;
+   do{
+      if(this->try_lock()){
+         break;
+      }
+      now = microsec_clock::universal_time();
+
+      if(now >= abs_time){
+         return false;
+      }
+      // relinquish current time slice
+      swait.yield();
+   }while (true);
+
+   return true;
+}
+
+inline void spin_mutex::unlock(void)
+{  ipcdetail::atomic_cas32(const_cast<boost::uint32_t*>(&m_s), 0, 1);   }
+
+}  //namespace ipcdetail {
+}  //namespace interprocess {
+}  //namespace boost {
+
+#include <boost/interprocess/detail/config_end.hpp>
+
+#endif   //BOOST_INTERPROCESS_DETAIL_SPIN_MUTEX_HPP