1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180
|
// Copyright (C) 2005 Davis E. King (davis@dlib.net)
// License: Boost Software License See LICENSE.txt for the full license.
#ifndef DLIB_AUTO_MUTEX_EXTENSIOn_
#define DLIB_AUTO_MUTEX_EXTENSIOn_
#include "threads_kernel.h"
#include "rmutex_extension.h"
#include "read_write_mutex_extension.h"
#include "auto_mutex_extension_abstract.h"
namespace dlib
{
// ----------------------------------------------------------------------------------------
class auto_mutex
{
/*!
INITIAL VALUE
- if (m != 0) then
- the mutex pointed to by m is locked
- if (r != 0) then
- the mutex pointed to by r is locked
- if (rw != 0) then
- the mutex pointed to by rw is locked
- exactly one of r, m, or rw is not 0.
CONVENTION
- if (m != 0) then
- the mutex pointed to by m is locked
- if (r != 0) then
- the mutex pointed to by r is locked
- if (rw != 0) then
- the mutex pointed to by rw is locked
- exactly one of r, m, or rw is not 0.
!*/
public:
explicit auto_mutex (
const mutex& m_
) : m(&m_),
r(0),
rw(0)
{
m->lock();
}
explicit auto_mutex (
const rmutex& r_
) : m(0),
r(&r_),
rw(0)
{
r->lock();
}
explicit auto_mutex (
const read_write_mutex& rw_
) : m(0),
r(0),
rw(&rw_)
{
rw->lock();
}
void unlock()
{
if (m != 0)
{
m->unlock();
m = 0;
}
else if (r != 0)
{
r->unlock();
r = 0;
}
else if (rw != 0)
{
rw->unlock();
rw = 0;
}
}
~auto_mutex (
)
{
unlock();
}
private:
const mutex* m;
const rmutex* r;
const read_write_mutex* rw;
// restricted functions
auto_mutex(auto_mutex&); // copy constructor
auto_mutex& operator=(auto_mutex&); // assignment operator
};
// ----------------------------------------------------------------------------------------
class auto_mutex_readonly
{
public:
explicit auto_mutex_readonly (
const read_write_mutex& rw_
) : rw(rw_), _has_write_lock(false), _has_read_lock(true)
{
rw.lock_readonly();
}
~auto_mutex_readonly (
)
{
unlock();
}
void lock_readonly (
)
{
if (!_has_read_lock)
{
unlock();
rw.lock_readonly();
_has_read_lock = true;
}
}
void lock_write (
)
{
if (!_has_write_lock)
{
unlock();
rw.lock();
_has_write_lock = true;
}
}
void unlock (
)
{
if (_has_write_lock)
{
rw.unlock();
_has_write_lock = false;
}
else if (_has_read_lock)
{
rw.unlock_readonly();
_has_read_lock = false;
}
}
bool has_read_lock (
) { return _has_read_lock; }
bool has_write_lock (
) { return _has_write_lock; }
private:
const read_write_mutex& rw;
bool _has_write_lock;
bool _has_read_lock;
// restricted functions
auto_mutex_readonly(auto_mutex_readonly&); // copy constructor
auto_mutex_readonly& operator=(auto_mutex_readonly&); // assignment operator
};
// ----------------------------------------------------------------------------------------
}
#endif // DLIB_AUTO_MUTEX_EXTENSIOn_
|