diff options
author | Mitya Selivanov <automainint@guattari.tech> | 2024-02-25 20:35:36 +0100 |
---|---|---|
committer | Mitya Selivanov <automainint@guattari.tech> | 2024-02-25 20:35:36 +0100 |
commit | e78124a094cf8751e44666fc4e44c6b7feac015d (patch) | |
tree | ed2f0e5ad673a0e5692c2283a800a1ec0d8e576d | |
parent | fec03e6f11b267dc90646c3c4d5458571ec74b7a (diff) | |
download | kit-e78124a094cf8751e44666fc4e44c6b7feac015d.zip |
Add shared mutex tests
-rw-r--r-- | source/kit/shared_mutex.h | 4 | ||||
-rw-r--r-- | source/tests/_exe.c | 1 | ||||
-rw-r--r-- | source/tests/shared_mutex.test.c | 93 |
3 files changed, 96 insertions, 2 deletions
diff --git a/source/kit/shared_mutex.h b/source/kit/shared_mutex.h index d202090..ad83418 100644 --- a/source/kit/shared_mutex.h +++ b/source/kit/shared_mutex.h @@ -47,7 +47,7 @@ static void kit_shared_mutex_init(kit_shared_mutex_t *m) { memory_order_relaxed); } -static i8 kit_shared_try_lock(kit_shared_mutex_t *m) { +static b8 kit_shared_try_lock(kit_shared_mutex_t *m) { assert(m != NULL); for (;;) { @@ -108,7 +108,7 @@ static void kit_shared_unlock(kit_shared_mutex_t *m) { assert(0); } -static i8 kit_unique_try_lock(kit_shared_mutex_t *m) { +static b8 kit_unique_try_lock(kit_shared_mutex_t *m) { assert(m != NULL); i8 prev_state = KIT_SHARED_MUTEX_READY; diff --git a/source/tests/_exe.c b/source/tests/_exe.c index 5509ab3..acbe5c2 100644 --- a/source/tests/_exe.c +++ b/source/tests/_exe.c @@ -15,6 +15,7 @@ #include "astar.test.c" #include "move_back.test.c" #include "mutex.test.c" +#include "shared_mutex.test.c" #include "secure_random.test.c" #include "sha256.test.c" #include "string_ref.test.c" diff --git a/source/tests/shared_mutex.test.c b/source/tests/shared_mutex.test.c new file mode 100644 index 0000000..9ee999b --- /dev/null +++ b/source/tests/shared_mutex.test.c @@ -0,0 +1,93 @@ +#include "../kit/shared_mutex.h" +#include "../kit/threads.h" + +#define KIT_TEST_FILE shared_mutex +#include "../kit/test.h" + +enum { + SHARED_MUTEX_TEST_SLEEP = 400000000, + SHARED_MUTEX_TEST_TICK_COUNT = 200, + SHARED_MUTEX_TEST_THREAD_COUNT = 100, +}; + +typedef struct { + shared_mutex_t lock; + int value; +} shared_mutex_test_data_t; + +static int shared_mutex_test_run_(void *data) { + shared_mutex_test_data_t *x = (shared_mutex_test_data_t *) data; + + for (i64 i = 0; i < SHARED_MUTEX_TEST_TICK_COUNT; i++) { + unique_lock(&x->lock); + + x->value += i; + thrd_yield(); + x->value -= i + 42; + thrd_yield(); + x->value += i + 20; + thrd_yield(); + x->value += 22 - i; + + unique_unlock(&x->lock); + } + + return 0; +} + +TEST("shared mutex lock") { + shared_mutex_test_data_t data; + thrd_t pool[SHARED_MUTEX_TEST_THREAD_COUNT]; + + data.value = 42; + shared_mutex_init(&data.lock); + + for (i64 i = 0; i < SHARED_MUTEX_TEST_THREAD_COUNT; i++) + thrd_create(pool + i, shared_mutex_test_run_, &data); + for (i64 i = 0; i < SHARED_MUTEX_TEST_THREAD_COUNT; i++) + thrd_join(pool[i], NULL); + + REQUIRE(data.value == 42); +} + +static int shared_mutex_test_lock_(void *data) { + shared_mutex_t *m = (shared_mutex_t *) data; + unique_lock(m); + + thrd_sleep( + &(struct timespec) { + .tv_sec = 0, + .tv_nsec = SHARED_MUTEX_TEST_SLEEP, + }, + NULL); + + unique_unlock(m); + + return 0; +} + +TEST("shared mutex try lock") { + shared_mutex_t m; + shared_mutex_init(&m); + + thrd_t t; + REQUIRE_EQ(thrd_create(&t, shared_mutex_test_lock_, &m), + thrd_success); + + REQUIRE_EQ(thrd_sleep( + &(struct timespec) { + .tv_sec = 0, + .tv_nsec = SHARED_MUTEX_TEST_SLEEP / 2, + }, + NULL), + thrd_success); + + REQUIRE_EQ(shared_try_lock(&m), 0); + + REQUIRE_EQ(thrd_join(t, NULL), thrd_success); + + REQUIRE_EQ(shared_try_lock(&m), 1); + shared_unlock(&m); +} + +#undef KIT_TEST_FILE |