1 //------------------------------------------------------------------------ 2 // Project : SDK Base 3 // Version : 1.0 4 // 5 // Category : Helpers 6 // Filename : base/thread/include/flock.h 7 // Created by : Steinberg, 1995 8 // Description : locks 9 // 10 //----------------------------------------------------------------------------- 11 // LICENSE 12 // (c) 2020, Steinberg Media Technologies GmbH, All Rights Reserved 13 //----------------------------------------------------------------------------- 14 // Redistribution and use in source and binary forms, with or without modification, 15 // are permitted provided that the following conditions are met: 16 // 17 // * Redistributions of source code must retain the above copyright notice, 18 // this list of conditions and the following disclaimer. 19 // * Redistributions in binary form must reproduce the above copyright notice, 20 // this list of conditions and the following disclaimer in the documentation 21 // and/or other materials provided with the distribution. 22 // * Neither the name of the Steinberg Media Technologies nor the names of its 23 // contributors may be used to endorse or promote products derived from this 24 // software without specific prior written permission. 25 // 26 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 27 // ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 28 // WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 29 // IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, 30 // INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 31 // BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 32 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 33 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE 34 // OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED 35 // OF THE POSSIBILITY OF SUCH DAMAGE. 36 //----------------------------------------------------------------------------- 37 38 //---------------------------------------------------------------------------------- 39 /** @file base/thread/include/flock.h 40 Locks. */ 41 /** @defgroup baseLocks Locks */ 42 //---------------------------------------------------------------------------------- 43 #pragma once 44 45 #include "base/source/fobject.h" 46 #include "pluginterfaces/base/ftypes.h" 47 48 #if SMTG_PTHREADS 49 #include <pthread.h> 50 51 #elif SMTG_OS_WINDOWS 52 struct CRITSECT // CRITICAL_SECTION 53 { 54 void* DebugInfo; // PRTL_CRITICAL_SECTION_DEBUG DebugInfo; 55 Steinberg::int32 LockCount; // LONG LockCount; 56 Steinberg::int32 RecursionCount; // LONG RecursionCount; 57 void* OwningThread; // HANDLE OwningThread 58 void* LockSemaphore; // HANDLE LockSemaphore 59 Steinberg::int32 SpinCount; // ULONG_PTR SpinCount 60 }; 61 #endif 62 63 namespace Steinberg { 64 namespace Base { 65 namespace Thread { 66 67 //------------------------------------------------------------------------ 68 /** Lock interface declaration. 69 @ingroup baseLocks */ 70 //------------------------------------------------------------------------ 71 struct ILock 72 { 73 //------------------------------------------------------------------------ ~ILockILock74 virtual ~ILock () {} 75 76 /** Enables lock. */ 77 virtual void lock () = 0; 78 79 /** Disables lock. */ 80 virtual void unlock () = 0; 81 82 /** Tries to disable lock. */ 83 virtual bool trylock () = 0; 84 //------------------------------------------------------------------------ 85 }; 86 87 //------------------------------------------------------------------------ 88 /** FLock declaration. 89 @ingroup baseLocks */ 90 //------------------------------------------------------------------------ 91 class FLock : public ILock 92 { 93 public: 94 //------------------------------------------------------------------------ 95 96 /** Lock constructor. 97 * @param name lock name 98 */ 99 FLock (const char8* name = "FLock"); 100 101 /** Lock destructor. */ 102 ~FLock (); 103 104 //-- ILock ----------------------------------------------------------- 105 virtual void lock () SMTG_OVERRIDE; 106 virtual void unlock () SMTG_OVERRIDE; 107 virtual bool trylock () SMTG_OVERRIDE; 108 109 //------------------------------------------------------------------------ 110 protected: 111 #if SMTG_PTHREADS 112 pthread_mutex_t mutex; ///< Mutex object 113 114 #elif SMTG_OS_WINDOWS 115 CRITSECT section; ///< Critical section object 116 #endif 117 }; 118 119 //------------------------------------------------------------------------ 120 /** FLockObj declaration. Reference counted lock 121 @ingroup baseLocks */ 122 //------------------------------------------------------------------------ 123 class FLockObject : public FObject, public FLock 124 { 125 public: 126 OBJ_METHODS (FLockObject, FObject) 127 }; 128 129 //------------------------------------------------------------------------ 130 /** FGuard - automatic object for locks. 131 @ingroup baseLocks */ 132 //------------------------------------------------------------------------ 133 class FGuard 134 { 135 public: 136 //------------------------------------------------------------------------ 137 138 /** FGuard constructor. 139 * @param _lock guard this lock 140 */ FGuard(ILock & _lock)141 FGuard (ILock& _lock) : lock (_lock) { lock.lock (); } 142 143 /** FGuard destructor. */ ~FGuard()144 ~FGuard () { lock.unlock (); } 145 146 //------------------------------------------------------------------------ 147 private: 148 ILock& lock; ///< guarded lock 149 }; 150 151 //------------------------------------------------------------------------ 152 /** Conditional Guard - Locks only if valid lock is passed. 153 @ingroup baseLocks */ 154 //------------------------------------------------------------------------ 155 class FConditionalGuard 156 { 157 public: 158 //------------------------------------------------------------------------ 159 160 /** FConditionGuard constructor. 161 * @param _lock guard this lock 162 */ FConditionalGuard(FLock * _lock)163 FConditionalGuard (FLock* _lock) : lock (_lock) 164 { 165 if (lock) 166 lock->lock (); 167 } 168 169 /** FConditionGuard destructor. */ ~FConditionalGuard()170 ~FConditionalGuard () 171 { 172 if (lock) 173 lock->unlock (); 174 } 175 176 //------------------------------------------------------------------------ 177 private: 178 FLock* lock; ///< guarded lock 179 }; 180 181 } // Thread 182 } // Base 183 } // Steinberg 184