Created
September 11, 2025 16:52
-
-
Save skeeto/ba145366b443715725e1f4763ef0298a to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <assert.h> | |
#include <pthread.h> | |
#include <stdint.h> | |
#include <stdlib.h> | |
#define lenof(a) (int)(sizeof(a) / sizeof(*(a))) | |
typedef uint16_t QueueUint; | |
typedef struct { | |
QueueUint head; | |
QueueUint tail; | |
uint64_t slots[1<<3]; | |
} Queue; | |
static void *consumer(void *arg) | |
{ | |
Queue *q = arg; | |
for (uint64_t v = 0;;) { | |
QueueUint head = q->head; | |
#if ACQUIRE | |
QueueUint tail = __atomic_load_n(&q->tail, __ATOMIC_ACQUIRE); | |
#else | |
QueueUint tail = q->tail; | |
#endif | |
if (tail != head) { | |
QueueUint len = lenof(q->slots); | |
uint64_t e = q->slots[head%len]; | |
__atomic_store_n(&q->head, head+1, __ATOMIC_RELEASE); | |
assert(e == v++); | |
} | |
} | |
} | |
int main() | |
{ | |
Queue *q = calloc(1, sizeof(*q)); | |
pthread_create(&(pthread_t){0}, 0, consumer, q); | |
for (uint64_t v = 0;;) { | |
#if ACQUIRE | |
QueueUint head = __atomic_load_n(&q->head, __ATOMIC_ACQUIRE); | |
#else | |
QueueUint head = q->head; | |
#endif | |
QueueUint tail = q->tail; | |
QueueUint len = lenof(q->slots); | |
if (tail != (QueueUint)(head + len)) { | |
q->slots[tail%len] = v++; | |
__atomic_store_n(&q->tail, tail+1, __ATOMIC_RELEASE); | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment