100.00% Lines (32/32) 100.00% Functions (9/9)
TLA Baseline Branch
Line Hits Code Line Hits Code
1   // 1   //
2   // Copyright (c) 2026 Michael Vandeberg 2   // Copyright (c) 2026 Michael Vandeberg
3   // 3   //
4   // Distributed under the Boost Software License, Version 1.0. (See accompanying 4   // Distributed under the Boost Software License, Version 1.0. (See accompanying
5   // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 5   // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6   // 6   //
7   // Official repository: https://github.com/cppalliance/corosio 7   // Official repository: https://github.com/cppalliance/corosio
8   // 8   //
9   9  
10   #ifndef BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP 10   #ifndef BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP
11   #define BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP 11   #define BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP
12   12  
13   #include <mutex> 13   #include <mutex>
14   14  
15   namespace boost::corosio::detail { 15   namespace boost::corosio::detail {
16   16  
17   /* Mutex wrapper that becomes a no-op when disabled. 17   /* Mutex wrapper that becomes a no-op when disabled.
18   18  
19   When enabled (the default), lock/unlock delegate to an 19   When enabled (the default), lock/unlock delegate to an
20   underlying std::mutex. When disabled, all operations are 20   underlying std::mutex. When disabled, all operations are
21   no-ops. The enabled flag is fixed after construction. 21   no-ops. The enabled flag is fixed after construction.
22   22  
23   scoped_lock wraps std::unique_lock<std::mutex> internally 23   scoped_lock wraps std::unique_lock<std::mutex> internally
24   so that condvar wait paths (which require the real lock 24   so that condvar wait paths (which require the real lock
25   type) compile and work in multi-threaded mode. 25   type) compile and work in multi-threaded mode.
26   */ 26   */
27   class conditionally_enabled_mutex 27   class conditionally_enabled_mutex
28   { 28   {
29   std::mutex mutex_; 29   std::mutex mutex_;
30   bool enabled_; 30   bool enabled_;
31   31  
32   public: 32   public:
HITCBC 33   19680 explicit conditionally_enabled_mutex(bool enabled = true) noexcept 33   19742 explicit conditionally_enabled_mutex(bool enabled = true) noexcept
HITCBC 34   19680 : enabled_(enabled) 34   19742 : enabled_(enabled)
35   { 35   {
HITCBC 36   19680 } 36   19742 }
37   37  
38 - conditionally_enabled_mutex(conditionally_enabled_mutex const&) = delete; 38 + conditionally_enabled_mutex(conditionally_enabled_mutex const&) = delete;
39 - conditionally_enabled_mutex& operator=(conditionally_enabled_mutex const&) = delete; 39 + conditionally_enabled_mutex&
  40 + operator=(conditionally_enabled_mutex const&) = delete;
40   41  
41   bool enabled() const noexcept 42   bool enabled() const noexcept
42   { 43   {
43   return enabled_; 44   return enabled_;
44   } 45   }
45   46  
HITCBC 46   12698 void set_enabled(bool v) noexcept 47   12740 void set_enabled(bool v) noexcept
47   { 48   {
HITCBC 48   12698 enabled_ = v; 49   12740 enabled_ = v;
HITCBC 49   12698 } 50   12740 }
50   51  
51   // Lockable interface — allows std::lock_guard<conditionally_enabled_mutex> 52   // Lockable interface — allows std::lock_guard<conditionally_enabled_mutex>
HITCBC 52 - 69201 void lock() { if (enabled_) mutex_.lock(); } 53 + 69473 void lock()
ECB 53 - 69201 void unlock() { if (enabled_) mutex_.unlock(); } 54 + {
HITGIC 54 - bool try_lock() { return !enabled_ || mutex_.try_lock(); } 55 + 69473 if (enabled_)
HITGNC   56 + 69473 mutex_.lock();
HITGNC   57 + 69473 }
HITGNC   58 + 69473 void unlock()
  59 + {
HITGNC   60 + 69473 if (enabled_)
HITGNC   61 + 69473 mutex_.unlock();
HITGNC   62 + 69473 }
  63 + bool try_lock()
  64 + {
  65 + return !enabled_ || mutex_.try_lock();
  66 + }
55   67  
56   class scoped_lock 68   class scoped_lock
57   { 69   {
58   std::unique_lock<std::mutex> lock_; 70   std::unique_lock<std::mutex> lock_;
59   bool enabled_; 71   bool enabled_;
60   72  
61   public: 73   public:
HITCBC 62   873858 explicit scoped_lock(conditionally_enabled_mutex& m) 74   875745 explicit scoped_lock(conditionally_enabled_mutex& m)
HITCBC 63   873858 : lock_(m.mutex_, std::defer_lock) 75   875745 : lock_(m.mutex_, std::defer_lock)
HITCBC 64   873858 , enabled_(m.enabled_) 76   875745 , enabled_(m.enabled_)
65   { 77   {
HITCBC 66   873858 if (enabled_) 78   875745 if (enabled_)
HITCBC 67   873838 lock_.lock(); 79   875725 lock_.lock();
HITCBC 68   873858 } 80   875745 }
69   81  
70   scoped_lock(scoped_lock const&) = delete; 82   scoped_lock(scoped_lock const&) = delete;
71   scoped_lock& operator=(scoped_lock const&) = delete; 83   scoped_lock& operator=(scoped_lock const&) = delete;
72   84  
HITCBC 73   818164 void lock() 85   819806 void lock()
74   { 86   {
HITCBC 75   818164 if (enabled_) 87   819806 if (enabled_)
HITCBC 76   818156 lock_.lock(); 88   819798 lock_.lock();
HITCBC 77   818164 } 89   819806 }
78   90  
HITCBC 79   831253 void unlock() 91   832906 void unlock()
80   { 92   {
HITCBC 81   831253 if (enabled_) 93   832906 if (enabled_)
HITCBC 82   831245 lock_.unlock(); 94   832898 lock_.unlock();
HITCBC 83   831253 } 95   832906 }
84   96  
HITCBC 85   827664 bool owns_lock() const noexcept 97   829136 bool owns_lock() const noexcept
86   { 98   {
HITCBC 87   827664 return enabled_ && lock_.owns_lock(); 99   829136 return enabled_ && lock_.owns_lock();
88   } 100   }
89   101  
90   // Access the underlying unique_lock for condvar wait(). 102   // Access the underlying unique_lock for condvar wait().
91   // Only called when locking is enabled. 103   // Only called when locking is enabled.
HITCBC 92   54 std::unique_lock<std::mutex>& underlying() noexcept 104   40 std::unique_lock<std::mutex>& underlying() noexcept
93   { 105   {
HITCBC 94   54 return lock_; 106   40 return lock_;
95   } 107   }
96   }; 108   };
97   }; 109   };
98   110  
99   } // namespace boost::corosio::detail 111   } // namespace boost::corosio::detail
100   112  
101   #endif // BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP 113   #endif // BOOST_COROSIO_DETAIL_CONDITIONALLY_ENABLED_MUTEX_HPP