pxl8/src/core/pxl8_queue.h

54 lines
1.7 KiB
C
Raw Normal View History

2026-01-31 09:31:17 -06:00
#pragma once
#include <stdatomic.h>
#include "pxl8_types.h"
#define PXL8_QUEUE_CAPACITY 256
typedef struct pxl8_queue {
void* items[PXL8_QUEUE_CAPACITY];
atomic_uint write_idx;
atomic_uint read_idx;
} pxl8_queue;
static inline void pxl8_queue_init(pxl8_queue* q) {
atomic_store(&q->write_idx, 0);
atomic_store(&q->read_idx, 0);
for (u32 i = 0; i < PXL8_QUEUE_CAPACITY; i++) {
q->items[i] = NULL;
}
}
static inline bool pxl8_queue_push(pxl8_queue* q, void* item) {
u32 w = atomic_load_explicit(&q->write_idx, memory_order_relaxed);
u32 next = (w + 1) % PXL8_QUEUE_CAPACITY;
if (next == atomic_load_explicit(&q->read_idx, memory_order_acquire)) {
return false;
}
q->items[w] = item;
atomic_store_explicit(&q->write_idx, next, memory_order_release);
return true;
}
static inline void* pxl8_queue_pop(pxl8_queue* q) {
u32 r = atomic_load_explicit(&q->read_idx, memory_order_relaxed);
if (r == atomic_load_explicit(&q->write_idx, memory_order_acquire)) {
return NULL;
}
void* item = q->items[r];
atomic_store_explicit(&q->read_idx, (r + 1) % PXL8_QUEUE_CAPACITY, memory_order_release);
return item;
}
static inline bool pxl8_queue_empty(const pxl8_queue* q) {
return atomic_load_explicit(&((pxl8_queue*)q)->read_idx, memory_order_acquire) ==
atomic_load_explicit(&((pxl8_queue*)q)->write_idx, memory_order_acquire);
}
static inline u32 pxl8_queue_count(const pxl8_queue* q) {
u32 w = atomic_load_explicit(&((pxl8_queue*)q)->write_idx, memory_order_acquire);
u32 r = atomic_load_explicit(&((pxl8_queue*)q)->read_idx, memory_order_acquire);
return (w >= r) ? (w - r) : (PXL8_QUEUE_CAPACITY - r + w);
}