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
|
/*************************************************
* Mutex Source File *
* (C) 1999-2005 The Botan Project *
*************************************************/
#include <botan/mutex.h>
#include <botan/exceptn.h>
#include <botan/init.h>
namespace Botan {
namespace {
/*************************************************
* Global Mutex Variables *
*************************************************/
Mutex* mutex_factory = 0;
Mutex* mutex_init_lock = 0;
/*************************************************
* Default Mutex *
*************************************************/
class Default_Mutex : public Mutex
{
public:
void lock();
void unlock();
Mutex* clone() const { return new Default_Mutex; }
Default_Mutex() { locked = false; }
private:
bool locked;
};
/*************************************************
* Lock the mutex *
*************************************************/
void Default_Mutex::lock()
{
if(locked)
throw Internal_Error("Default_Mutex::lock: Mutex is already locked");
locked = true;
}
/*************************************************
* Unlock the mutex *
*************************************************/
void Default_Mutex::unlock()
{
if(!locked)
throw Internal_Error("Default_Mutex::unlock: Mutex is already unlocked");
locked = false;
}
}
/*************************************************
* Get a mew mutex *
*************************************************/
Mutex* get_mutex()
{
if(mutex_factory == 0)
return new Default_Mutex;
return mutex_factory->clone();
}
/*************************************************
* Initialize a mutex atomically *
*************************************************/
void initialize_mutex(Mutex*& mutex)
{
if(mutex) return;
if(mutex_init_lock)
{
Mutex_Holder lock(mutex_init_lock);
if(mutex == 0)
mutex = get_mutex();
}
else
mutex = get_mutex();
}
namespace Init {
/*************************************************
* Set the Mutex type *
*************************************************/
void set_mutex_type(Mutex* mutex)
{
delete mutex_factory;
delete mutex_init_lock;
mutex_factory = mutex;
if(mutex) mutex_init_lock = get_mutex();
else mutex_init_lock = 0;
}
}
}
|