1 #include <stdlib.h>
2 #include <string.h>
3 #include "ring.h"
4
ring_alloc(Ring * ring,int capacity)5 void ring_alloc(Ring *ring, int capacity) {
6 ring->capacity = capacity;
7 ring->start = 0;
8 ring->end = 0;
9 ring->data = (RingEntry *)calloc(capacity, sizeof(RingEntry));
10 }
11
ring_free(Ring * ring)12 void ring_free(Ring *ring) {
13 free(ring->data);
14 }
15
ring_empty(Ring * ring)16 int ring_empty(Ring *ring) {
17 return ring->start == ring->end;
18 }
19
ring_full(Ring * ring)20 int ring_full(Ring *ring) {
21 return ring->start == (ring->end + 1) % ring->capacity;
22 }
23
ring_size(Ring * ring)24 int ring_size(Ring *ring) {
25 if (ring->end >= ring->start) {
26 return ring->end - ring->start;
27 }
28 else {
29 return ring->capacity - (ring->start - ring->end);
30 }
31 }
32
ring_grow(Ring * ring)33 void ring_grow(Ring *ring) {
34 Ring new_ring;
35 RingEntry entry;
36 ring_alloc(&new_ring, ring->capacity * 2);
37 while (ring_get(ring, &entry)) {
38 ring_put(&new_ring, &entry);
39 }
40 free(ring->data);
41 ring->capacity = new_ring.capacity;
42 ring->start = new_ring.start;
43 ring->end = new_ring.end;
44 ring->data = new_ring.data;
45 }
46
ring_put(Ring * ring,RingEntry * entry)47 void ring_put(Ring *ring, RingEntry *entry) {
48 if (ring_full(ring)) {
49 ring_grow(ring);
50 }
51 RingEntry *e = ring->data + ring->end;
52 memcpy(e, entry, sizeof(RingEntry));
53 ring->end = (ring->end + 1) % ring->capacity;
54 }
55
ring_put_block(Ring * ring,int p,int q,int x,int y,int z,int w)56 void ring_put_block(Ring *ring, int p, int q, int x, int y, int z, int w) {
57 RingEntry entry;
58 entry.type = BLOCK;
59 entry.p = p;
60 entry.q = q;
61 entry.x = x;
62 entry.y = y;
63 entry.z = z;
64 entry.w = w;
65 ring_put(ring, &entry);
66 }
67
ring_put_light(Ring * ring,int p,int q,int x,int y,int z,int w)68 void ring_put_light(Ring *ring, int p, int q, int x, int y, int z, int w) {
69 RingEntry entry;
70 entry.type = LIGHT;
71 entry.p = p;
72 entry.q = q;
73 entry.x = x;
74 entry.y = y;
75 entry.z = z;
76 entry.w = w;
77 ring_put(ring, &entry);
78 }
79
ring_put_key(Ring * ring,int p,int q,int key)80 void ring_put_key(Ring *ring, int p, int q, int key) {
81 RingEntry entry;
82 entry.type = KEY;
83 entry.p = p;
84 entry.q = q;
85 entry.key = key;
86 ring_put(ring, &entry);
87 }
88
ring_put_commit(Ring * ring)89 void ring_put_commit(Ring *ring) {
90 RingEntry entry;
91 entry.type = COMMIT;
92 ring_put(ring, &entry);
93 }
94
ring_put_exit(Ring * ring)95 void ring_put_exit(Ring *ring) {
96 RingEntry entry;
97 entry.type = EXIT;
98 ring_put(ring, &entry);
99 }
100
ring_get(Ring * ring,RingEntry * entry)101 int ring_get(Ring *ring, RingEntry *entry) {
102 if (ring_empty(ring)) {
103 return 0;
104 }
105 RingEntry *e = ring->data + ring->start;
106 memcpy(entry, e, sizeof(RingEntry));
107 ring->start = (ring->start + 1) % ring->capacity;
108 return 1;
109 }
110