1 a0d146ed 2005-07-12 devnull #include "stdinc.h"
2 a0d146ed 2005-07-12 devnull #include "dat.h"
3 a0d146ed 2005-07-12 devnull #include "fns.h"
5 a0d146ed 2005-07-12 devnull typedef struct LumpQueue LumpQueue;
6 a0d146ed 2005-07-12 devnull typedef struct WLump WLump;
10 a0d146ed 2005-07-12 devnull MaxLumpQ = 1 << 3 /* max. lumps on a single write queue, must be pow 2 */
13 a0d146ed 2005-07-12 devnull struct WLump
16 a0d146ed 2005-07-12 devnull Packet *p;
17 a0d146ed 2005-07-12 devnull int creator;
22 a0d146ed 2005-07-12 devnull struct LumpQueue
24 a0d146ed 2005-07-12 devnull QLock lock;
25 a0d146ed 2005-07-12 devnull Rendez flush;
26 a0d146ed 2005-07-12 devnull Rendez full;
27 a0d146ed 2005-07-12 devnull Rendez empty;
28 a0d146ed 2005-07-12 devnull WLump q[MaxLumpQ];
33 a0d146ed 2005-07-12 devnull static LumpQueue *lumpqs;
34 a0d146ed 2005-07-12 devnull static int nqs;
36 a0d146ed 2005-07-12 devnull static QLock glk;
37 a0d146ed 2005-07-12 devnull static int gen;
39 a0d146ed 2005-07-12 devnull static void queueproc(void *vq);
42 a0d146ed 2005-07-12 devnull initlumpqueues(int nq)
44 a0d146ed 2005-07-12 devnull LumpQueue *q;
47 a0d146ed 2005-07-12 devnull nqs = nq;
49 a0d146ed 2005-07-12 devnull lumpqs = MKNZ(LumpQueue, nq);
51 a0d146ed 2005-07-12 devnull for(i = 0; i < nq; i++){
52 a0d146ed 2005-07-12 devnull q = &lumpqs[i];
53 a0d146ed 2005-07-12 devnull q->full.l = &q->lock;
54 a0d146ed 2005-07-12 devnull q->empty.l = &q->lock;
55 a0d146ed 2005-07-12 devnull q->flush.l = &q->lock;
57 a0d146ed 2005-07-12 devnull if(vtproc(queueproc, q) < 0){
58 a0d146ed 2005-07-12 devnull seterr(EOk, "can't start write queue slave: %r");
59 a0d146ed 2005-07-12 devnull return -1;
61 a0d146ed 2005-07-12 devnull if(vtproc(queueproc, q) < 0){
62 a0d146ed 2005-07-12 devnull seterr(EOk, "can't start write queue slave: %r");
63 a0d146ed 2005-07-12 devnull return -1;
65 a0d146ed 2005-07-12 devnull if(vtproc(queueproc, q) < 0){
66 a0d146ed 2005-07-12 devnull seterr(EOk, "can't start write queue slave: %r");
67 a0d146ed 2005-07-12 devnull return -1;
69 a0d146ed 2005-07-12 devnull if(vtproc(queueproc, q) < 0){
70 a0d146ed 2005-07-12 devnull seterr(EOk, "can't start write queue slave: %r");
71 a0d146ed 2005-07-12 devnull return -1;
73 a0d146ed 2005-07-12 devnull if(vtproc(queueproc, q) < 0){
74 a0d146ed 2005-07-12 devnull seterr(EOk, "can't start write queue slave: %r");
75 a0d146ed 2005-07-12 devnull return -1;
79 a0d146ed 2005-07-12 devnull return 0;
83 a0d146ed 2005-07-12 devnull * queue a lump & it's packet data for writing
86 a0d146ed 2005-07-12 devnull queuewrite(Lump *u, Packet *p, int creator, uint ms)
88 a0d146ed 2005-07-12 devnull LumpQueue *q;
91 a0d146ed 2005-07-12 devnull trace(TraceProc, "queuewrite");
92 a0d146ed 2005-07-12 devnull i = indexsect(mainindex, u->score);
93 a0d146ed 2005-07-12 devnull if(i < 0 || i >= nqs){
94 a0d146ed 2005-07-12 devnull seterr(EBug, "internal error: illegal index section in queuewrite");
95 a0d146ed 2005-07-12 devnull return -1;
98 a0d146ed 2005-07-12 devnull q = &lumpqs[i];
100 a0d146ed 2005-07-12 devnull qlock(&q->lock);
101 a0d146ed 2005-07-12 devnull while(q->r == ((q->w + 1) & (MaxLumpQ - 1))){
102 a0d146ed 2005-07-12 devnull trace(TraceProc, "queuewrite sleep");
103 a0d146ed 2005-07-12 devnull rsleep(&q->full);
106 a0d146ed 2005-07-12 devnull q->q[q->w].u = u;
107 a0d146ed 2005-07-12 devnull q->q[q->w].p = p;
108 a0d146ed 2005-07-12 devnull q->q[q->w].creator = creator;
109 a0d146ed 2005-07-12 devnull q->q[q->w].ms = ms;
110 a0d146ed 2005-07-12 devnull q->q[q->w].gen = gen;
111 a0d146ed 2005-07-12 devnull q->w = (q->w + 1) & (MaxLumpQ - 1);
113 a0d146ed 2005-07-12 devnull trace(TraceProc, "queuewrite wakeup");
114 a0d146ed 2005-07-12 devnull rwakeup(&q->empty);
116 a0d146ed 2005-07-12 devnull qunlock(&q->lock);
118 a0d146ed 2005-07-12 devnull return 0;
122 a0d146ed 2005-07-12 devnull flushqueue(void)
125 a0d146ed 2005-07-12 devnull LumpQueue *q;
127 a0d146ed 2005-07-12 devnull if(!lumpqs)
130 a0d146ed 2005-07-12 devnull trace(TraceProc, "flushqueue");
132 a0d146ed 2005-07-12 devnull qlock(&glk);
134 a0d146ed 2005-07-12 devnull qunlock(&glk);
136 a0d146ed 2005-07-12 devnull for(i=0; i<mainindex->nsects; i++){
137 a0d146ed 2005-07-12 devnull q = &lumpqs[i];
138 a0d146ed 2005-07-12 devnull qlock(&q->lock);
139 a0d146ed 2005-07-12 devnull while(q->w != q->r && gen - q->q[q->r].gen > 0){
140 a0d146ed 2005-07-12 devnull trace(TraceProc, "flushqueue sleep q%d", i);
141 a0d146ed 2005-07-12 devnull rsleep(&q->flush);
143 a0d146ed 2005-07-12 devnull qunlock(&q->lock);
147 a0d146ed 2005-07-12 devnull static void
148 a0d146ed 2005-07-12 devnull queueproc(void *vq)
150 a0d146ed 2005-07-12 devnull LumpQueue *q;
151 a0d146ed 2005-07-12 devnull Lump *u;
152 a0d146ed 2005-07-12 devnull Packet *p;
153 a0d146ed 2005-07-12 devnull int creator;
154 a0d146ed 2005-07-12 devnull uint ms;
156 a0d146ed 2005-07-12 devnull threadsetname("queueproc");
159 a0d146ed 2005-07-12 devnull for(;;){
160 a0d146ed 2005-07-12 devnull qlock(&q->lock);
161 a0d146ed 2005-07-12 devnull while(q->w == q->r){
162 a0d146ed 2005-07-12 devnull trace(TraceProc, "queueproc sleep empty");
163 a0d146ed 2005-07-12 devnull rsleep(&q->empty);
166 a0d146ed 2005-07-12 devnull u = q->q[q->r].u;
167 a0d146ed 2005-07-12 devnull p = q->q[q->r].p;
168 a0d146ed 2005-07-12 devnull creator = q->q[q->r].creator;
169 a0d146ed 2005-07-12 devnull ms = q->q[q->r].ms;
171 a0d146ed 2005-07-12 devnull q->r = (q->r + 1) & (MaxLumpQ - 1);
172 a0d146ed 2005-07-12 devnull trace(TraceProc, "queueproc wakeup flush");
173 a0d146ed 2005-07-12 devnull rwakeupall(&q->flush);
175 a0d146ed 2005-07-12 devnull trace(TraceProc, "queueproc wakeup full");
176 a0d146ed 2005-07-12 devnull rwakeup(&q->full);
178 a0d146ed 2005-07-12 devnull qunlock(&q->lock);
180 a0d146ed 2005-07-12 devnull trace(TraceProc, "queueproc writelump %V", u->score);
181 a0d146ed 2005-07-12 devnull if(writeqlump(u, p, creator, ms) < 0)
182 a0d146ed 2005-07-12 devnull fprint(2, "failed to write lump for %V: %r", u->score);
183 a0d146ed 2005-07-12 devnull trace(TraceProc, "queueproc wrotelump %V", u->score);
185 a0d146ed 2005-07-12 devnull putlump(u);