1 // 2 // detail/conditionally_enabled_event.hpp 3 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 4 // 5 // Copyright (c) 2003-2021 Christopher M. Kohlhoff (chris at kohlhoff dot com) 6 // 7 // Distributed under the Boost Software License, Version 1.0. (See accompanying 8 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 9 // 10 11 #ifndef BOOST_ASIO_DETAIL_CONDITIONALLY_ENABLED_EVENT_HPP 12 #define BOOST_ASIO_DETAIL_CONDITIONALLY_ENABLED_EVENT_HPP 13 14 #if defined(_MSC_VER) && (_MSC_VER >= 1200) 15 # pragma once 16 #endif // defined(_MSC_VER) && (_MSC_VER >= 1200) 17 18 #include <boost/asio/detail/config.hpp> 19 #include <boost/asio/detail/conditionally_enabled_mutex.hpp> 20 #include <boost/asio/detail/event.hpp> 21 #include <boost/asio/detail/noncopyable.hpp> 22 #include <boost/asio/detail/null_event.hpp> 23 #include <boost/asio/detail/scoped_lock.hpp> 24 25 #include <boost/asio/detail/push_options.hpp> 26 27 namespace boost { 28 namespace asio { 29 namespace detail { 30 31 // Mutex adapter used to conditionally enable or disable locking. 32 class conditionally_enabled_event 33 : private noncopyable 34 { 35 public: 36 // Constructor. conditionally_enabled_event()37 conditionally_enabled_event() 38 { 39 } 40 41 // Destructor. ~conditionally_enabled_event()42 ~conditionally_enabled_event() 43 { 44 } 45 46 // Signal the event. (Retained for backward compatibility.) signal(conditionally_enabled_mutex::scoped_lock & lock)47 void signal(conditionally_enabled_mutex::scoped_lock& lock) 48 { 49 if (lock.mutex_.enabled_) 50 event_.signal(lock); 51 } 52 53 // Signal all waiters. signal_all(conditionally_enabled_mutex::scoped_lock & lock)54 void signal_all(conditionally_enabled_mutex::scoped_lock& lock) 55 { 56 if (lock.mutex_.enabled_) 57 event_.signal_all(lock); 58 } 59 60 // Unlock the mutex and signal one waiter. unlock_and_signal_one(conditionally_enabled_mutex::scoped_lock & lock)61 void unlock_and_signal_one( 62 conditionally_enabled_mutex::scoped_lock& lock) 63 { 64 if (lock.mutex_.enabled_) 65 event_.unlock_and_signal_one(lock); 66 } 67 68 // Unlock the mutex and signal one waiter who may destroy us. unlock_and_signal_one_for_destruction(conditionally_enabled_mutex::scoped_lock & lock)69 void unlock_and_signal_one_for_destruction( 70 conditionally_enabled_mutex::scoped_lock& lock) 71 { 72 if (lock.mutex_.enabled_) 73 event_.unlock_and_signal_one(lock); 74 } 75 76 // If there's a waiter, unlock the mutex and signal it. maybe_unlock_and_signal_one(conditionally_enabled_mutex::scoped_lock & lock)77 bool maybe_unlock_and_signal_one( 78 conditionally_enabled_mutex::scoped_lock& lock) 79 { 80 if (lock.mutex_.enabled_) 81 return event_.maybe_unlock_and_signal_one(lock); 82 else 83 return false; 84 } 85 86 // Reset the event. clear(conditionally_enabled_mutex::scoped_lock & lock)87 void clear(conditionally_enabled_mutex::scoped_lock& lock) 88 { 89 if (lock.mutex_.enabled_) 90 event_.clear(lock); 91 } 92 93 // Wait for the event to become signalled. wait(conditionally_enabled_mutex::scoped_lock & lock)94 void wait(conditionally_enabled_mutex::scoped_lock& lock) 95 { 96 if (lock.mutex_.enabled_) 97 event_.wait(lock); 98 else 99 null_event().wait(lock); 100 } 101 102 // Timed wait for the event to become signalled. wait_for_usec(conditionally_enabled_mutex::scoped_lock & lock,long usec)103 bool wait_for_usec( 104 conditionally_enabled_mutex::scoped_lock& lock, long usec) 105 { 106 if (lock.mutex_.enabled_) 107 return event_.wait_for_usec(lock, usec); 108 else 109 return null_event().wait_for_usec(lock, usec); 110 } 111 112 private: 113 boost::asio::detail::event event_; 114 }; 115 116 } // namespace detail 117 } // namespace asio 118 } // namespace boost 119 120 #include <boost/asio/detail/pop_options.hpp> 121 122 #endif // BOOST_ASIO_DETAIL_CONDITIONALLY_ENABLED_EVENT_HPP 123