1#include <math/align.h>
2#include <mem/alloc.h>
3#include <mem/buddy.h>
4#include <mem/pmm.h>
5#include <mem/vmm.h>
6#include <string.h>
7
8#include "internal.h"
9
10bool domain_free_queue_enqueue(struct domain_free_queue *fq, paddr_t addr,
11 size_t pages) {
12 bool success = false;
13 enum irql irql = spin_lock(lock: &fq->lock);
14
15 size_t next = (fq->tail + 1) % fq->capacity;
16 if (next != fq->head) {
17 fq->queue[fq->tail].addr = addr;
18 fq->queue[fq->tail].pages = pages;
19 fq->tail = next;
20 success = true;
21 }
22
23 if (success)
24 atomic_fetch_add_explicit(&fq->num_elements, 1, memory_order_relaxed);
25
26 spin_unlock(lock: &fq->lock, old: irql);
27 return success;
28}
29
30bool domain_free_queue_dequeue(struct domain_free_queue *fq, paddr_t *addr_out,
31 size_t *pages_out) {
32 bool success = false;
33 enum irql irql = spin_lock(lock: &fq->lock);
34
35 if (fq->head != fq->tail) {
36 *addr_out = fq->queue[fq->head].addr;
37 *pages_out = fq->queue[fq->head].pages;
38 fq->head = (fq->head + 1) % fq->capacity;
39 success = true;
40 }
41
42 if (success)
43 atomic_fetch_sub_explicit(&fq->num_elements, 1, memory_order_relaxed);
44
45 spin_unlock(lock: &fq->lock, old: irql);
46 return success;
47}
48