[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[RFC] Implementing a simple mutex using simple locks and futex calls
From: |
Marin Ramesa |
Subject: |
[RFC] Implementing a simple mutex using simple locks and futex calls |
Date: |
Mon, 23 Sep 2013 09:13:25 +0200 |
This is a second test and proof of concept for the new futex
call. Please comment on this. I don't know if I used the simple locks
correctly (this time I at least initialized it).
The idea is to implement a simple mutex using one atomic operation
combined with futex calls.
First, the code:
#include <lock.h>
#include <futex.h>
struct mutex {
decl_simple_lock_data(, inc_lock);
int value;
};
typedef struct mutex *mutex_t;
void mutex_init(mutex_t mtx);
int atomic_inc(mutex_t mtx);
void mutex_lock(mutex_t mtx);
void mutex_unlock(mutex_t mtx);
void mutex_init(mutex_t mtx)
{
simple_lock_init(&(mtx->inc_lock));
mtx->value = 0;
return;
}
int atomic_inc(mutex_t mtx)
{
int ret = mtx->value;
simple_lock(&(mtx->inc_lock);
mtx->value++;
simple_unlock(&(mtx->inc_lock));
return ret;
}
void mutex_lock(mutex_t mtx)
{
int count;
while ((count = atomic_inc(mtx)) != 0)
futex(&(mtx->value), count + 1, FUTEX_WAIT);
return;
}
void mutex_unlock(mutex_t mtx)
{
mtx->value = 0;
futex(&(mtx->value), 1, FUTEX_WAKE);
return;
}
Mutex initializes with the value zero, which means that the
mutex is not taken. All other values mean that the mutex is
taken. So, thread 1 competes for the mutex and calls mutex_lock(),
mutex's value gets atomically increased and the old value gets
saved in the variable count. If the count is zero, thread 1
enters the critical region and takes the mutex. Thread 2 calls
mutex_lock() while the mutex value is 1 and gets suspended in the
futex. The count is now 1 which means there is one thread that
will eventually return to compete for the mutex. This happens when
thread 1 calls mutex_unlock() which resets the mutex's value to zero
and wakes one thread.