From 9cffe521f32bcf3a6d69825b38b5dcf21ed9d774 Mon Sep 17 00:00:00 2001 From: wnstngs <64602598+wnstngs@users.noreply.github.com> Date: Wed, 7 Oct 2026 10:32:08 +0300 Subject: [PATCH] kernel: use circular lists in various places --- kernel-src/fs/abc.c | 9 +++++---- kernel-src/fs/vfs.c | 3 ++- kernel-src/io/input.c | 2 +- kernel-src/io/net/raw.c | 4 ++-- kernel-src/sys/syscalls/futex.c | 10 +++++++++- kernel-src/sys/work.c | 8 ++++---- 6 files changed, 23 insertions(+), 13 deletions(-) diff --git a/kernel-src/fs/abc.c b/kernel-src/fs/abc.c index 59e32ad0..85d8d7a7 100644 --- a/kernel-src/fs/abc.c +++ b/kernel-src/fs/abc.c @@ -39,7 +39,7 @@ static list_node_t *try_stealing_from_dirty(abc_t *abc, uint64_t block) { if ((__atomic_load_n(&blk->flags, __ATOMIC_RELAXED) & ABC_BLOCK_FLAGS_DIRTY) == 0) return NULL; - list_remove(&abc->dirty_list, &blk->dirty_list_node); + list_remove(&blk->dirty_list_node); __atomic_exchange_n(&blk->flags, ABC_BLOCK_FLAGS_BUSY, __ATOMIC_ACQUIRE); return &blk->dirty_list_node; } @@ -50,7 +50,7 @@ void abc_sync(abc_t *abc) { EVENT_ATTACH(&listener, &abc->dirty_list_empty_event); pushlock_acquire_exclusive(&abc->dirty_list_lock); - if (abc->dirty_list.head == NULL && !abc->syncing) { + if (list_is_empty(&abc->dirty_list) && !abc->syncing) { pushlock_release_exclusive(&abc->dirty_list_lock); EVENT_DETACHALL(&listener); return; @@ -133,7 +133,7 @@ static void writer_thread(void) { pushlock_release_shared(&abc->lock); pushlock_release_exclusive(&abc->dirty_list_lock); - abc_block_t *front_block = (abc_block_t *)internal_list.head; + abc_block_t *front_block = (abc_block_t *)list_get_first(&internal_list); size_t blocks_per_page = PAGE_SIZE / abc->block_size; size_t iovec_count = (block_count + front_block->block % blocks_per_page + blocks_per_page - 1) / blocks_per_page; iovec_t iovec[iovec_count]; @@ -164,7 +164,8 @@ static void writer_thread(void) { __assert(written == block_count * abc->block_size); } - list_for_each_safe(&internal_list, list_node) { + list_node_t *list_node; + while ((list_node = list_pop_front(&internal_list)) != NULL) { abc_block_t *blk = (abc_block_t *)list_node; if (__atomic_and_fetch(&blk->flags, ~ABC_BLOCK_FLAGS_BUSY, __ATOMIC_ACQUIRE) & ABC_BLOCK_FLAGS_DIRTY) { pushlock_acquire_exclusive(&abc->dirty_list_lock); diff --git a/kernel-src/fs/vfs.c b/kernel-src/fs/vfs.c index 4580ca7e..714426f8 100644 --- a/kernel-src/fs/vfs.c +++ b/kernel-src/fs/vfs.c @@ -59,7 +59,8 @@ void vfs_root_event_signal(void) { root_mounted = true; MUTEX_RELEASE(&root_event_mutex); - list_for_each_safe (&root_event_list, node) { + list_node_t *node; + while ((node = list_pop_front(&root_event_list)) != NULL) { root_event_waiter_t *rew = (root_event_waiter_t *)node; rew->fn(rew->ctx); free(rew); diff --git a/kernel-src/io/input.c b/kernel-src/io/input.c index 58a60305..af133a31 100644 --- a/kernel-src/io/input.c +++ b/kernel-src/io/input.c @@ -142,7 +142,7 @@ static int input_listener_close(int minor, int flags) { MUTEX_RELEASE(&input_dev_table_lock); long ipl = spinlock_acquire_raise_ipl(&lis->device->lock, IPL_INPUT); - list_remove(&lis->device->listeners, &lis->node); + list_remove(&lis->node); spinlock_release_lower_ipl(&lis->device->lock, ipl); ringbuffer_destroy(&lis->buffer); diff --git a/kernel-src/io/net/raw.c b/kernel-src/io/net/raw.c index 11a7fc14..3c668b56 100644 --- a/kernel-src/io/net/raw.c +++ b/kernel-src/io/net/raw.c @@ -11,7 +11,7 @@ #define SOCKET_BUFFER (16 * 1024) SPINLOCK_DEFINE(list_lock); -static list_t socket_list; +static list_t socket_list = LIST_INIT_VALUE(socket_list); typedef struct { uint8_t sender[6]; @@ -260,7 +260,7 @@ static int raw_getpeername(socket_t *socket, sockaddr_t *addr) { static void raw_destroy(socket_t *handle) { raw_socket_t *socket = (raw_socket_t *)handle; long ipl = spinlock_acquire_raise_ipl(&list_lock, IPL_DPC); - list_remove(&socket_list, &socket->list_node); + list_remove(&socket->list_node); spinlock_release_lower_ipl(&list_lock, ipl); free(socket); } diff --git a/kernel-src/sys/syscalls/futex.c b/kernel-src/sys/syscalls/futex.c index 7825bf24..66bdfc65 100644 --- a/kernel-src/sys/syscalls/futex.c +++ b/kernel-src/sys/syscalls/futex.c @@ -1,4 +1,5 @@ #include +#include #include #include #include @@ -94,7 +95,7 @@ static int wait_on_bucket(futex_bucket_t *bucket, uintptr_t key, size_t timeoutu else if (state == ENTRY_STATE_TIMEOUT) error = ETIMEDOUT; - list_remove(&bucket->list, &entry.list_node); + list_remove(&entry.list_node); MUTEX_RELEASE(&bucket->mutex); @@ -180,3 +181,10 @@ syscallret_t syscall_futex(context_t *, uint32_t *futexp, int op, uint32_t value mm_unlock_and_release_page(physical); return ret; } + +static void futex_init(void) { + for (size_t i = 0; i < BUCKET_COUNT; ++i) + list_init(&buckets[i].list); +} + +INIT_ROUTINE_DEFINE(futex, INIT_ROUTINE_FLAGS_NONE, futex_init, bsp_early); diff --git a/kernel-src/sys/work.c b/kernel-src/sys/work.c index 9fb66564..1b011609 100644 --- a/kernel-src/sys/work.c +++ b/kernel-src/sys/work.c @@ -32,11 +32,11 @@ static bool work_active(work_queue_t *wq, work_t *work) { } static void wake_waiters(work_queue_t *wq, work_t *work) { - list_for_each_safe (&wq->waiter_list, node) { + list_for_each_safe (&wq->waiter_list, node, next) { work_waiter_t *ww = (work_waiter_t *)node; if (ww->work == work) { - list_remove(&wq->waiter_list, &ww->list_node); + list_remove(&ww->list_node); sched_wakeup(ww->thread, SCHED_WAKEUP_REASON_NORMAL); } } @@ -83,7 +83,7 @@ static void worker() { ipl = spinlock_acquire_raise_ipl(&wq->lock, wq->lock_ipl); wake_waiters(wq, work); - list_remove(&wq->active_list, &aw.list_node); + list_remove(&aw.list_node); spinlock_release_lower_ipl(&wq->lock, ipl); } } @@ -163,7 +163,7 @@ int work_dequeue(work_queue_t *wq, work_t *work) { goto leave; wake_waiters(wq, work); - list_remove(&wq->work_list, &work->list_node); + list_remove(&work->list_node); work->pending = 0; leave: