Skip to content

Commit

Permalink
mutex: introduce uacpi_recursive_lock
Browse files Browse the repository at this point in the history
Signed-off-by: Daniil Tatianin <99danilt@gmail.com>
  • Loading branch information
d-tatianin committed Dec 16, 2024
1 parent 1066242 commit 875d0f4
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 0 deletions.
12 changes: 12 additions & 0 deletions include/uacpi/internal/mutex.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,18 @@ static inline uacpi_status uacpi_release_native_mutex_may_be_null(
return UACPI_STATUS_OK;
}

struct uacpi_recursive_lock {
uacpi_handle mutex;
uacpi_size depth;
uacpi_thread_id owner;
};

uacpi_status uacpi_recursive_lock_init(struct uacpi_recursive_lock *lock);
uacpi_status uacpi_recursive_lock_deinit(struct uacpi_recursive_lock *lock);

uacpi_status uacpi_recursive_lock_acquire(struct uacpi_recursive_lock *lock);
uacpi_status uacpi_recursive_lock_release(struct uacpi_recursive_lock *lock);

struct uacpi_rw_lock {
uacpi_handle read_mutex;
uacpi_handle write_mutex;
Expand Down
61 changes: 61 additions & 0 deletions source/mutex.c
Original file line number Diff line number Diff line change
Expand Up @@ -250,6 +250,67 @@ uacpi_status uacpi_release_aml_mutex(uacpi_mutex *mutex)
return UACPI_STATUS_OK;
}

uacpi_status uacpi_recursive_lock_init(struct uacpi_recursive_lock *lock)
{
lock->mutex = uacpi_kernel_create_mutex();
if (uacpi_unlikely(lock->mutex == UACPI_NULL))
return UACPI_STATUS_OUT_OF_MEMORY;

lock->owner = UACPI_THREAD_ID_NONE;
lock->depth = 0;

return UACPI_STATUS_OK;
}

uacpi_status uacpi_recursive_lock_deinit(struct uacpi_recursive_lock *lock)
{
if (uacpi_unlikely(lock->depth)) {
uacpi_warn(
"de-initializing active recursive lock %p with depth=%zu\n",
lock, lock->depth
);
lock->depth = 0;
}

lock->owner = UACPI_THREAD_ID_NONE;

if (lock->mutex != UACPI_NULL) {
uacpi_kernel_free_mutex(lock->mutex);
lock->mutex = UACPI_NULL;
}

return UACPI_STATUS_OK;
}

uacpi_status uacpi_recursive_lock_acquire(struct uacpi_recursive_lock *lock)
{
uacpi_thread_id this_id;
uacpi_status ret = UACPI_STATUS_OK;

this_id = uacpi_kernel_get_thread_id();
if (UACPI_ATOMIC_LOAD_THREAD_ID(&lock->owner) == this_id) {
lock->depth++;
return ret;
}

ret = uacpi_acquire_native_mutex(lock->mutex);
if (uacpi_unlikely_error(ret))
return ret;

UACPI_ATOMIC_STORE_THREAD_ID(&lock->owner, this_id);
lock->depth = 1;
return ret;
}

uacpi_status uacpi_recursive_lock_release(struct uacpi_recursive_lock *lock)
{
if (lock->depth-- > 1)
return UACPI_STATUS_OK;

UACPI_ATOMIC_STORE_THREAD_ID(&lock->owner, UACPI_THREAD_ID_NONE);
return uacpi_release_native_mutex(lock->mutex);
}

uacpi_status uacpi_rw_lock_init(struct uacpi_rw_lock *lock)
{
lock->read_mutex = uacpi_kernel_create_mutex();
Expand Down

0 comments on commit 875d0f4

Please sign in to comment.