From f410026b7bc96dbb42fec3839dc5d2e41b12f4a4 Mon Sep 17 00:00:00 2001 From: "Luke T. Shumaker" Date: Sat, 28 Sep 2024 20:50:36 -0600 Subject: misc --- libcr_ipc/CMakeLists.txt | 1 + libcr_ipc/include/libcr_ipc/mutex.h | 46 +++++++++++++++++++++++++++++++++++++ libcr_ipc/include/libcr_ipc/sema.h | 6 ++++- libcr_ipc/mutex.c | 37 +++++++++++++++++++++++++++++ libcr_ipc/sema.c | 3 +-- 5 files changed, 90 insertions(+), 3 deletions(-) create mode 100644 libcr_ipc/include/libcr_ipc/mutex.h create mode 100644 libcr_ipc/mutex.c (limited to 'libcr_ipc') diff --git a/libcr_ipc/CMakeLists.txt b/libcr_ipc/CMakeLists.txt index 3388fcd..957b638 100644 --- a/libcr_ipc/CMakeLists.txt +++ b/libcr_ipc/CMakeLists.txt @@ -7,6 +7,7 @@ add_library(libcr_ipc INTERFACE) target_include_directories(libcr_ipc SYSTEM INTERFACE ${CMAKE_CURRENT_LIST_DIR}/include) target_sources(libcr_ipc INTERFACE sema.c + mutex.c ) target_link_libraries(libcr_ipc INTERFACE libcr diff --git a/libcr_ipc/include/libcr_ipc/mutex.h b/libcr_ipc/include/libcr_ipc/mutex.h new file mode 100644 index 0000000..38ebde0 --- /dev/null +++ b/libcr_ipc/include/libcr_ipc/mutex.h @@ -0,0 +1,46 @@ +/* libcr_ipc/mutex.h - Simple mutexes for libcr (header file) + * + * Copyright (C) 2024 Luke T. Shumaker + * SPDX-Licence-Identifier: AGPL-3.0-or-later + */ + +#ifndef _COROUTINE_MUTEX_H_ +#define _COROUTINE_MUTEX_H_ + +#include /* for bool */ + +#include /* for cid_t */ + +struct _cr_mutex_cid_list { + cid_t val; + struct _cr_mutex_cid_list *next; +}; + +/** + * A cr_mutex_t is a fair mutex. + */ +typedef struct { + bool locked; + struct _cr_mutex_cid_list *head, **tail; +} cr_mutex_t; + +/** + * Lock the mutex. Blocks if it is already locked. + * + * @blocks maybe + * @yields maybe + * @run_in coroutine + */ +void cr_mutex_lock(cr_mutex_t *); + +/** + * Unlock the mutex. Unblocks a coroutine that is blocked on + * cr_mutex_lock(). + * + * @blocks never + * @yields never + * @may_run_in coroutine + */ +void cr_mutex_unluck(cr_mutex_t *); + +#endif /* _COROUTINE_MUTEX_H_ */ diff --git a/libcr_ipc/include/libcr_ipc/sema.h b/libcr_ipc/include/libcr_ipc/sema.h index a2a176d..454eb5d 100644 --- a/libcr_ipc/include/libcr_ipc/sema.h +++ b/libcr_ipc/include/libcr_ipc/sema.h @@ -1,4 +1,4 @@ -/* coroutine_sema.h - Simple semaphores for coroutine.{h,c} +/* libcr_ipc/sema.h - Simple semaphores for libcr (header file) * * Copyright (C) 2024 Luke T. Shumaker * SPDX-Licence-Identifier: AGPL-3.0-or-later @@ -7,6 +7,10 @@ #ifndef _COROUTINE_SEMA_H_ #define _COROUTINE_SEMA_H_ +#include /* for bool */ + +#include /* for cid_t */ + struct _cr_sema_cid_list { cid_t val; struct _cr_sema_cid_list *next; diff --git a/libcr_ipc/mutex.c b/libcr_ipc/mutex.c new file mode 100644 index 0000000..c5cea96 --- /dev/null +++ b/libcr_ipc/mutex.c @@ -0,0 +1,37 @@ +/* libcr_ipc/mutex.c - Simple mutexes for libcr (implementation file) + * + * Copyright (C) 2024 Luke T. Shumaker + * SPDX-Licence-Identifier: AGPL-3.0-or-later + */ + +#include + +void cr_mutex_lock(cr_mutex_t *mu) { + assert(mu); + if (!mu->tail) + mu->tail = &mu->head; + if (!mu->locked) { + mu->locked = true; + return; + } + struct _cr_mutex_cid_list self = { + .val = cr_getcid(), + .next = NULL, + }; + *(mu->tail) = &self; + mu->tail = &(self.next); + cr_pause_and_yield(); +} + +void cr_mutex_unlock(cr_mutex_t *mu) { + assert(mu); + assert(mu->tail); + assert(mu->locked); + if (mu->head) { + cr_unpause(mu->head->val); + mu->head = mu->head->next; + if (!mu->head) + mu->tail = &mu->head; + } else + mu->locked = false; +} diff --git a/libcr_ipc/sema.c b/libcr_ipc/sema.c index a3b2ca0..9645a41 100644 --- a/libcr_ipc/sema.c +++ b/libcr_ipc/sema.c @@ -1,4 +1,4 @@ -/* coroutine_sema.h - Simple semaphores for coroutine.{h,c} +/* libcr_ipc/sema.c - Simple semaphores for libcr (implementation file) * * Copyright (C) 2024 Luke T. Shumaker * SPDX-Licence-Identifier: AGPL-3.0-or-later @@ -6,7 +6,6 @@ #include -#include #include /** Drain the sema->{head,tail} list. Returns true if cr_getcid() was drained. */ -- cgit v1.2.3-2-g168b