PMDK C++ bindings  1.13.0-git107.g7e59f08f
This is the C++ bindings documentation for PMDK's libpmemobj.
timed_mutex.hpp
Go to the documentation of this file.
1 // SPDX-License-Identifier: BSD-3-Clause
2 /* Copyright 2016-2021, Intel Corporation */
3 
9 #ifndef LIBPMEMOBJ_CPP_TIMED_MUTEX_HPP
10 #define LIBPMEMOBJ_CPP_TIMED_MUTEX_HPP
11 
12 #include <chrono>
13 
15 #include <libpmemobj/thread.h>
16 
17 namespace pmem
18 {
19 
20 namespace obj
21 {
22 
34 class timed_mutex {
35  typedef std::chrono::system_clock clock_type;
36 
37 public:
39  typedef PMEMmutex *native_handle_type;
40 
47  {
48  PMEMobjpool *pop;
49  if ((pop = pmemobj_pool_by_ptr(&plock)) == nullptr)
50  throw pmem::lock_error(
51  1, std::generic_category(),
52  "Persistent mutex not from persistent memory.");
53 
54  pmemobj_mutex_zero(pop, &plock);
55  }
56 
60  ~timed_mutex() = default;
61 
73  void
74  lock()
75  {
76  PMEMobjpool *pop = pmemobj_pool_by_ptr(this);
77  if (int ret = pmemobj_mutex_lock(pop, &this->plock))
78  throw detail::exception_with_errormsg<lock_error>(
79  ret, std::system_category(),
80  "Failed to lock a mutex.");
81  }
82 
97  bool
99  {
100  PMEMobjpool *pop = pmemobj_pool_by_ptr(this);
101  int ret = pmemobj_mutex_trylock(pop, &this->plock);
102 
103  if (ret == 0)
104  return true;
105  else if (ret == EBUSY)
106  return false;
107  else
108  throw detail::exception_with_errormsg<lock_error>(
109  ret, std::system_category(),
110  "Failed to lock a mutex.");
111  }
112 
130  template <typename Clock, typename Duration>
131  bool
133  const std::chrono::time_point<Clock, Duration> &timeout_time)
134  {
135  return timedlock_impl(timeout_time);
136  }
137 
155  template <typename Rep, typename Period>
156  bool
157  try_lock_for(const std::chrono::duration<Rep, Period> &timeout_duration)
158  {
159  return timedlock_impl(clock_type::now() + timeout_duration);
160  }
161 
169  void
171  {
172  PMEMobjpool *pop = pmemobj_pool_by_ptr(this);
173  int ret = pmemobj_mutex_unlock(pop, &this->plock);
174  if (ret)
175  throw detail::exception_with_errormsg<lock_error>(
176  ret, std::system_category(),
177  "Failed to unlock a mutex.");
178  }
179 
186  native_handle() noexcept
187  {
188  return &this->plock;
189  }
190 
194  timed_mutex &operator=(const timed_mutex &) = delete;
195 
199  timed_mutex(const timed_mutex &) = delete;
200 
201 private:
205  template <typename Clock, typename Duration>
206  bool
207  timedlock_impl(const std::chrono::time_point<Clock, Duration> &abs_time)
208  {
209  PMEMobjpool *pop = pmemobj_pool_by_ptr(this);
210 
211  /* convert to my clock */
212  const typename Clock::time_point their_now = Clock::now();
213  const clock_type::time_point my_now = clock_type::now();
214  const auto delta = abs_time - their_now;
215  const auto my_abs = my_now + delta;
216 
217  struct timespec ts = detail::timepoint_to_timespec(my_abs);
218 
219  auto ret = pmemobj_mutex_timedlock(pop, &this->plock, &ts);
220 
221  if (ret == 0)
222  return true;
223  else if (ret == ETIMEDOUT)
224  return false;
225  else
226  throw detail::exception_with_errormsg<lock_error>(
227  ret, std::system_category(),
228  "Failed to lock a mutex");
229  }
230 
232  PMEMmutex plock;
233 };
234 
235 } /* namespace obj */
236 
237 } /* namespace pmem */
238 
239 #endif /* LIBPMEMOBJ_CPP_TIMED_MUTEX_HPP */
Custom lock error class.
Definition: pexceptions.hpp:121
Persistent memory resident timed_mutex implementation.
Definition: timed_mutex.hpp:34
void lock()
Locks the mutex, blocks if already locked.
Definition: timed_mutex.hpp:74
native_handle_type native_handle() noexcept
Access a native handle to this condition variable.
Definition: timed_mutex.hpp:186
void unlock()
Unlocks a previously locked mutex.
Definition: timed_mutex.hpp:170
bool try_lock_until(const std::chrono::time_point< Clock, Duration > &timeout_time)
Makes the current thread block until the lock is acquired or a specific time is reached.
Definition: timed_mutex.hpp:132
timed_mutex()
Default constructor.
Definition: timed_mutex.hpp:46
timed_mutex(const timed_mutex &)=delete
Deleted copy constructor.
~timed_mutex()=default
Defaulted destructor.
bool try_lock()
Tries to lock the mutex, returns regardless if the lock succeeds.
Definition: timed_mutex.hpp:98
PMEMmutex * native_handle_type
Implementation defined handle to the native type.
Definition: timed_mutex.hpp:39
bool try_lock_for(const std::chrono::duration< Rep, Period > &timeout_duration)
Makes the current thread block until the lock is acquired or a specified amount of time passes.
Definition: timed_mutex.hpp:157
timed_mutex & operator=(const timed_mutex &)=delete
Deleted assignment operator.
Commonly used conversions.
timespec timepoint_to_timespec(const std::chrono::time_point< Clock, Duration > &timepoint)
Convert std::chrono::time_point to posix timespec.
Definition: conversions.hpp:30
Persistent memory namespace.
Definition: allocation_flag.hpp:15