root / sys-queue.h @ a245f2e7
History | View | Annotate | Download (16.9 kB)
1 | 23cde8bb | aliguori | /* $NetBSD: queue.h,v 1.45.14.1 2007/07/18 20:13:24 liamjfoy Exp $ */
|
---|---|---|---|
2 | 23cde8bb | aliguori | |
3 | 23cde8bb | aliguori | /*
|
4 | 23cde8bb | aliguori | * Qemu version: Copy from netbsd, removed debug code, removed some of
|
5 | 23cde8bb | aliguori | * the implementations. Left in lists, tail queues and circular queues.
|
6 | 23cde8bb | aliguori | */
|
7 | 23cde8bb | aliguori | |
8 | 23cde8bb | aliguori | /*
|
9 | 23cde8bb | aliguori | * Copyright (c) 1991, 1993
|
10 | 23cde8bb | aliguori | * The Regents of the University of California. All rights reserved.
|
11 | 23cde8bb | aliguori | *
|
12 | 23cde8bb | aliguori | * Redistribution and use in source and binary forms, with or without
|
13 | 23cde8bb | aliguori | * modification, are permitted provided that the following conditions
|
14 | 23cde8bb | aliguori | * are met:
|
15 | 23cde8bb | aliguori | * 1. Redistributions of source code must retain the above copyright
|
16 | 23cde8bb | aliguori | * notice, this list of conditions and the following disclaimer.
|
17 | 23cde8bb | aliguori | * 2. Redistributions in binary form must reproduce the above copyright
|
18 | 23cde8bb | aliguori | * notice, this list of conditions and the following disclaimer in the
|
19 | 23cde8bb | aliguori | * documentation and/or other materials provided with the distribution.
|
20 | 23cde8bb | aliguori | * 3. Neither the name of the University nor the names of its contributors
|
21 | 23cde8bb | aliguori | * may be used to endorse or promote products derived from this software
|
22 | 23cde8bb | aliguori | * without specific prior written permission.
|
23 | 23cde8bb | aliguori | *
|
24 | 23cde8bb | aliguori | * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
25 | 23cde8bb | aliguori | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
26 | 23cde8bb | aliguori | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
27 | 23cde8bb | aliguori | * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
28 | 23cde8bb | aliguori | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
29 | 23cde8bb | aliguori | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
30 | 23cde8bb | aliguori | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
31 | 23cde8bb | aliguori | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
32 | 23cde8bb | aliguori | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
33 | 23cde8bb | aliguori | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
34 | 23cde8bb | aliguori | * SUCH DAMAGE.
|
35 | 23cde8bb | aliguori | *
|
36 | 23cde8bb | aliguori | * @(#)queue.h 8.5 (Berkeley) 8/20/94
|
37 | 23cde8bb | aliguori | */
|
38 | 23cde8bb | aliguori | |
39 | 23cde8bb | aliguori | #ifndef _SYS_QUEUE_H_
|
40 | 23cde8bb | aliguori | #define _SYS_QUEUE_H_
|
41 | 23cde8bb | aliguori | |
42 | 23cde8bb | aliguori | /*
|
43 | 23cde8bb | aliguori | * This file defines three types of data structures:
|
44 | 23cde8bb | aliguori | * lists, tail queues, and circular queues.
|
45 | 23cde8bb | aliguori | *
|
46 | 23cde8bb | aliguori | * A list is headed by a single forward pointer (or an array of forward
|
47 | 23cde8bb | aliguori | * pointers for a hash table header). The elements are doubly linked
|
48 | 23cde8bb | aliguori | * so that an arbitrary element can be removed without a need to
|
49 | 23cde8bb | aliguori | * traverse the list. New elements can be added to the list before
|
50 | 23cde8bb | aliguori | * or after an existing element or at the head of the list. A list
|
51 | 23cde8bb | aliguori | * may only be traversed in the forward direction.
|
52 | 23cde8bb | aliguori | *
|
53 | 23cde8bb | aliguori | * A tail queue is headed by a pair of pointers, one to the head of the
|
54 | 23cde8bb | aliguori | * list and the other to the tail of the list. The elements are doubly
|
55 | 23cde8bb | aliguori | * linked so that an arbitrary element can be removed without a need to
|
56 | 23cde8bb | aliguori | * traverse the list. New elements can be added to the list before or
|
57 | 23cde8bb | aliguori | * after an existing element, at the head of the list, or at the end of
|
58 | 23cde8bb | aliguori | * the list. A tail queue may be traversed in either direction.
|
59 | 23cde8bb | aliguori | *
|
60 | 23cde8bb | aliguori | * A circle queue is headed by a pair of pointers, one to the head of the
|
61 | 23cde8bb | aliguori | * list and the other to the tail of the list. The elements are doubly
|
62 | 23cde8bb | aliguori | * linked so that an arbitrary element can be removed without a need to
|
63 | 23cde8bb | aliguori | * traverse the list. New elements can be added to the list before or after
|
64 | 23cde8bb | aliguori | * an existing element, at the head of the list, or at the end of the list.
|
65 | 23cde8bb | aliguori | * A circle queue may be traversed in either direction, but has a more
|
66 | 23cde8bb | aliguori | * complex end of list detection.
|
67 | 23cde8bb | aliguori | *
|
68 | 23cde8bb | aliguori | * For details on the use of these macros, see the queue(3) manual page.
|
69 | 23cde8bb | aliguori | */
|
70 | 23cde8bb | aliguori | |
71 | 23cde8bb | aliguori | /*
|
72 | 23cde8bb | aliguori | * List definitions.
|
73 | 23cde8bb | aliguori | */
|
74 | 23cde8bb | aliguori | #define LIST_HEAD(name, type) \
|
75 | 23cde8bb | aliguori | struct name { \
|
76 | 23cde8bb | aliguori | struct type *lh_first; /* first element */ \ |
77 | 23cde8bb | aliguori | } |
78 | 23cde8bb | aliguori | |
79 | 23cde8bb | aliguori | #define LIST_HEAD_INITIALIZER(head) \
|
80 | 23cde8bb | aliguori | { NULL }
|
81 | 23cde8bb | aliguori | |
82 | 23cde8bb | aliguori | #define LIST_ENTRY(type) \
|
83 | 23cde8bb | aliguori | struct { \
|
84 | 23cde8bb | aliguori | struct type *le_next; /* next element */ \ |
85 | 23cde8bb | aliguori | struct type **le_prev; /* address of previous next element */ \ |
86 | 23cde8bb | aliguori | } |
87 | 23cde8bb | aliguori | |
88 | 23cde8bb | aliguori | /*
|
89 | 23cde8bb | aliguori | * List functions.
|
90 | 23cde8bb | aliguori | */
|
91 | 23cde8bb | aliguori | #define LIST_INIT(head) do { \ |
92 | 23cde8bb | aliguori | (head)->lh_first = NULL; \
|
93 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
94 | 23cde8bb | aliguori | |
95 | 23cde8bb | aliguori | #define LIST_INSERT_AFTER(listelm, elm, field) do { \ |
96 | 23cde8bb | aliguori | if (((elm)->field.le_next = (listelm)->field.le_next) != NULL) \ |
97 | 23cde8bb | aliguori | (listelm)->field.le_next->field.le_prev = \ |
98 | 23cde8bb | aliguori | &(elm)->field.le_next; \ |
99 | 23cde8bb | aliguori | (listelm)->field.le_next = (elm); \ |
100 | 23cde8bb | aliguori | (elm)->field.le_prev = &(listelm)->field.le_next; \ |
101 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
102 | 23cde8bb | aliguori | |
103 | 23cde8bb | aliguori | #define LIST_INSERT_BEFORE(listelm, elm, field) do { \ |
104 | 23cde8bb | aliguori | (elm)->field.le_prev = (listelm)->field.le_prev; \ |
105 | 23cde8bb | aliguori | (elm)->field.le_next = (listelm); \ |
106 | 23cde8bb | aliguori | *(listelm)->field.le_prev = (elm); \ |
107 | 23cde8bb | aliguori | (listelm)->field.le_prev = &(elm)->field.le_next; \ |
108 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
109 | 23cde8bb | aliguori | |
110 | 23cde8bb | aliguori | #define LIST_INSERT_HEAD(head, elm, field) do { \ |
111 | 23cde8bb | aliguori | if (((elm)->field.le_next = (head)->lh_first) != NULL) \ |
112 | 23cde8bb | aliguori | (head)->lh_first->field.le_prev = &(elm)->field.le_next;\ |
113 | 23cde8bb | aliguori | (head)->lh_first = (elm); \ |
114 | 23cde8bb | aliguori | (elm)->field.le_prev = &(head)->lh_first; \ |
115 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
116 | 23cde8bb | aliguori | |
117 | 23cde8bb | aliguori | #define LIST_REMOVE(elm, field) do { \ |
118 | 23cde8bb | aliguori | if ((elm)->field.le_next != NULL) \ |
119 | 23cde8bb | aliguori | (elm)->field.le_next->field.le_prev = \ |
120 | 23cde8bb | aliguori | (elm)->field.le_prev; \ |
121 | 23cde8bb | aliguori | *(elm)->field.le_prev = (elm)->field.le_next; \ |
122 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
123 | 23cde8bb | aliguori | |
124 | 23cde8bb | aliguori | #define LIST_FOREACH(var, head, field) \
|
125 | 23cde8bb | aliguori | for ((var) = ((head)->lh_first); \
|
126 | 23cde8bb | aliguori | (var); \ |
127 | 23cde8bb | aliguori | (var) = ((var)->field.le_next)) |
128 | 23cde8bb | aliguori | |
129 | 23cde8bb | aliguori | /*
|
130 | 23cde8bb | aliguori | * List access methods.
|
131 | 23cde8bb | aliguori | */
|
132 | 23cde8bb | aliguori | #define LIST_EMPTY(head) ((head)->lh_first == NULL) |
133 | 23cde8bb | aliguori | #define LIST_FIRST(head) ((head)->lh_first)
|
134 | 23cde8bb | aliguori | #define LIST_NEXT(elm, field) ((elm)->field.le_next)
|
135 | 23cde8bb | aliguori | |
136 | 23cde8bb | aliguori | |
137 | 23cde8bb | aliguori | /*
|
138 | 23cde8bb | aliguori | * Tail queue definitions.
|
139 | 23cde8bb | aliguori | */
|
140 | 23cde8bb | aliguori | #define _TAILQ_HEAD(name, type, qual) \
|
141 | 23cde8bb | aliguori | struct name { \
|
142 | 23cde8bb | aliguori | qual type *tqh_first; /* first element */ \
|
143 | 23cde8bb | aliguori | qual type *qual *tqh_last; /* addr of last next element */ \
|
144 | 23cde8bb | aliguori | } |
145 | 23cde8bb | aliguori | #define TAILQ_HEAD(name, type) _TAILQ_HEAD(name, struct type,) |
146 | 23cde8bb | aliguori | |
147 | 23cde8bb | aliguori | #define TAILQ_HEAD_INITIALIZER(head) \
|
148 | 23cde8bb | aliguori | { NULL, &(head).tqh_first }
|
149 | 23cde8bb | aliguori | |
150 | 23cde8bb | aliguori | #define _TAILQ_ENTRY(type, qual) \
|
151 | 23cde8bb | aliguori | struct { \
|
152 | 23cde8bb | aliguori | qual type *tqe_next; /* next element */ \
|
153 | 23cde8bb | aliguori | qual type *qual *tqe_prev; /* address of previous next element */\
|
154 | 23cde8bb | aliguori | } |
155 | 23cde8bb | aliguori | #define TAILQ_ENTRY(type) _TAILQ_ENTRY(struct type,) |
156 | 23cde8bb | aliguori | |
157 | 23cde8bb | aliguori | /*
|
158 | 23cde8bb | aliguori | * Tail queue functions.
|
159 | 23cde8bb | aliguori | */
|
160 | 23cde8bb | aliguori | #define TAILQ_INIT(head) do { \ |
161 | 23cde8bb | aliguori | (head)->tqh_first = NULL; \
|
162 | 23cde8bb | aliguori | (head)->tqh_last = &(head)->tqh_first; \ |
163 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
164 | 23cde8bb | aliguori | |
165 | 23cde8bb | aliguori | #define TAILQ_INSERT_HEAD(head, elm, field) do { \ |
166 | 23cde8bb | aliguori | if (((elm)->field.tqe_next = (head)->tqh_first) != NULL) \ |
167 | 23cde8bb | aliguori | (head)->tqh_first->field.tqe_prev = \ |
168 | 23cde8bb | aliguori | &(elm)->field.tqe_next; \ |
169 | 23cde8bb | aliguori | else \
|
170 | 23cde8bb | aliguori | (head)->tqh_last = &(elm)->field.tqe_next; \ |
171 | 23cde8bb | aliguori | (head)->tqh_first = (elm); \ |
172 | 23cde8bb | aliguori | (elm)->field.tqe_prev = &(head)->tqh_first; \ |
173 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
174 | 23cde8bb | aliguori | |
175 | 23cde8bb | aliguori | #define TAILQ_INSERT_TAIL(head, elm, field) do { \ |
176 | 23cde8bb | aliguori | (elm)->field.tqe_next = NULL; \
|
177 | 23cde8bb | aliguori | (elm)->field.tqe_prev = (head)->tqh_last; \ |
178 | 23cde8bb | aliguori | *(head)->tqh_last = (elm); \ |
179 | 23cde8bb | aliguori | (head)->tqh_last = &(elm)->field.tqe_next; \ |
180 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
181 | 23cde8bb | aliguori | |
182 | 23cde8bb | aliguori | #define TAILQ_INSERT_AFTER(head, listelm, elm, field) do { \ |
183 | 23cde8bb | aliguori | if (((elm)->field.tqe_next = (listelm)->field.tqe_next) != NULL)\ |
184 | 23cde8bb | aliguori | (elm)->field.tqe_next->field.tqe_prev = \ |
185 | 23cde8bb | aliguori | &(elm)->field.tqe_next; \ |
186 | 23cde8bb | aliguori | else \
|
187 | 23cde8bb | aliguori | (head)->tqh_last = &(elm)->field.tqe_next; \ |
188 | 23cde8bb | aliguori | (listelm)->field.tqe_next = (elm); \ |
189 | 23cde8bb | aliguori | (elm)->field.tqe_prev = &(listelm)->field.tqe_next; \ |
190 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
191 | 23cde8bb | aliguori | |
192 | 23cde8bb | aliguori | #define TAILQ_INSERT_BEFORE(listelm, elm, field) do { \ |
193 | 23cde8bb | aliguori | (elm)->field.tqe_prev = (listelm)->field.tqe_prev; \ |
194 | 23cde8bb | aliguori | (elm)->field.tqe_next = (listelm); \ |
195 | 23cde8bb | aliguori | *(listelm)->field.tqe_prev = (elm); \ |
196 | 23cde8bb | aliguori | (listelm)->field.tqe_prev = &(elm)->field.tqe_next; \ |
197 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
198 | 23cde8bb | aliguori | |
199 | 23cde8bb | aliguori | #define TAILQ_REMOVE(head, elm, field) do { \ |
200 | 23cde8bb | aliguori | if (((elm)->field.tqe_next) != NULL) \ |
201 | 23cde8bb | aliguori | (elm)->field.tqe_next->field.tqe_prev = \ |
202 | 23cde8bb | aliguori | (elm)->field.tqe_prev; \ |
203 | 23cde8bb | aliguori | else \
|
204 | 23cde8bb | aliguori | (head)->tqh_last = (elm)->field.tqe_prev; \ |
205 | 23cde8bb | aliguori | *(elm)->field.tqe_prev = (elm)->field.tqe_next; \ |
206 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
207 | 23cde8bb | aliguori | |
208 | 23cde8bb | aliguori | #define TAILQ_FOREACH(var, head, field) \
|
209 | 23cde8bb | aliguori | for ((var) = ((head)->tqh_first); \
|
210 | 23cde8bb | aliguori | (var); \ |
211 | 23cde8bb | aliguori | (var) = ((var)->field.tqe_next)) |
212 | 23cde8bb | aliguori | |
213 | 23cde8bb | aliguori | #define TAILQ_FOREACH_REVERSE(var, head, headname, field) \
|
214 | 23cde8bb | aliguori | for ((var) = (*(((struct headname *)((head)->tqh_last))->tqh_last)); \ |
215 | 23cde8bb | aliguori | (var); \ |
216 | 23cde8bb | aliguori | (var) = (*(((struct headname *)((var)->field.tqe_prev))->tqh_last)))
|
217 | 23cde8bb | aliguori | |
218 | 23cde8bb | aliguori | /*
|
219 | 23cde8bb | aliguori | * Tail queue access methods.
|
220 | 23cde8bb | aliguori | */
|
221 | 23cde8bb | aliguori | #define TAILQ_EMPTY(head) ((head)->tqh_first == NULL) |
222 | 23cde8bb | aliguori | #define TAILQ_FIRST(head) ((head)->tqh_first)
|
223 | 23cde8bb | aliguori | #define TAILQ_NEXT(elm, field) ((elm)->field.tqe_next)
|
224 | 23cde8bb | aliguori | |
225 | 23cde8bb | aliguori | #define TAILQ_LAST(head, headname) \
|
226 | 23cde8bb | aliguori | (*(((struct headname *)((head)->tqh_last))->tqh_last))
|
227 | 23cde8bb | aliguori | #define TAILQ_PREV(elm, headname, field) \
|
228 | 23cde8bb | aliguori | (*(((struct headname *)((elm)->field.tqe_prev))->tqh_last))
|
229 | 23cde8bb | aliguori | |
230 | 23cde8bb | aliguori | |
231 | 23cde8bb | aliguori | /*
|
232 | 23cde8bb | aliguori | * Circular queue definitions.
|
233 | 23cde8bb | aliguori | */
|
234 | 23cde8bb | aliguori | #define CIRCLEQ_HEAD(name, type) \
|
235 | 23cde8bb | aliguori | struct name { \
|
236 | 23cde8bb | aliguori | struct type *cqh_first; /* first element */ \ |
237 | 23cde8bb | aliguori | struct type *cqh_last; /* last element */ \ |
238 | 23cde8bb | aliguori | } |
239 | 23cde8bb | aliguori | |
240 | 23cde8bb | aliguori | #define CIRCLEQ_HEAD_INITIALIZER(head) \
|
241 | 23cde8bb | aliguori | { (void *)&head, (void *)&head } |
242 | 23cde8bb | aliguori | |
243 | 23cde8bb | aliguori | #define CIRCLEQ_ENTRY(type) \
|
244 | 23cde8bb | aliguori | struct { \
|
245 | 23cde8bb | aliguori | struct type *cqe_next; /* next element */ \ |
246 | 23cde8bb | aliguori | struct type *cqe_prev; /* previous element */ \ |
247 | 23cde8bb | aliguori | } |
248 | 23cde8bb | aliguori | |
249 | 23cde8bb | aliguori | /*
|
250 | 23cde8bb | aliguori | * Circular queue functions.
|
251 | 23cde8bb | aliguori | */
|
252 | 23cde8bb | aliguori | #define CIRCLEQ_INIT(head) do { \ |
253 | 23cde8bb | aliguori | (head)->cqh_first = (void *)(head); \
|
254 | 23cde8bb | aliguori | (head)->cqh_last = (void *)(head); \
|
255 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
256 | 23cde8bb | aliguori | |
257 | 23cde8bb | aliguori | #define CIRCLEQ_INSERT_AFTER(head, listelm, elm, field) do { \ |
258 | 23cde8bb | aliguori | (elm)->field.cqe_next = (listelm)->field.cqe_next; \ |
259 | 23cde8bb | aliguori | (elm)->field.cqe_prev = (listelm); \ |
260 | 23cde8bb | aliguori | if ((listelm)->field.cqe_next == (void *)(head)) \ |
261 | 23cde8bb | aliguori | (head)->cqh_last = (elm); \ |
262 | 23cde8bb | aliguori | else \
|
263 | 23cde8bb | aliguori | (listelm)->field.cqe_next->field.cqe_prev = (elm); \ |
264 | 23cde8bb | aliguori | (listelm)->field.cqe_next = (elm); \ |
265 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
266 | 23cde8bb | aliguori | |
267 | 23cde8bb | aliguori | #define CIRCLEQ_INSERT_BEFORE(head, listelm, elm, field) do { \ |
268 | 23cde8bb | aliguori | (elm)->field.cqe_next = (listelm); \ |
269 | 23cde8bb | aliguori | (elm)->field.cqe_prev = (listelm)->field.cqe_prev; \ |
270 | 23cde8bb | aliguori | if ((listelm)->field.cqe_prev == (void *)(head)) \ |
271 | 23cde8bb | aliguori | (head)->cqh_first = (elm); \ |
272 | 23cde8bb | aliguori | else \
|
273 | 23cde8bb | aliguori | (listelm)->field.cqe_prev->field.cqe_next = (elm); \ |
274 | 23cde8bb | aliguori | (listelm)->field.cqe_prev = (elm); \ |
275 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
276 | 23cde8bb | aliguori | |
277 | 23cde8bb | aliguori | #define CIRCLEQ_INSERT_HEAD(head, elm, field) do { \ |
278 | 23cde8bb | aliguori | (elm)->field.cqe_next = (head)->cqh_first; \ |
279 | 23cde8bb | aliguori | (elm)->field.cqe_prev = (void *)(head); \
|
280 | 23cde8bb | aliguori | if ((head)->cqh_last == (void *)(head)) \ |
281 | 23cde8bb | aliguori | (head)->cqh_last = (elm); \ |
282 | 23cde8bb | aliguori | else \
|
283 | 23cde8bb | aliguori | (head)->cqh_first->field.cqe_prev = (elm); \ |
284 | 23cde8bb | aliguori | (head)->cqh_first = (elm); \ |
285 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
286 | 23cde8bb | aliguori | |
287 | 23cde8bb | aliguori | #define CIRCLEQ_INSERT_TAIL(head, elm, field) do { \ |
288 | 23cde8bb | aliguori | (elm)->field.cqe_next = (void *)(head); \
|
289 | 23cde8bb | aliguori | (elm)->field.cqe_prev = (head)->cqh_last; \ |
290 | 23cde8bb | aliguori | if ((head)->cqh_first == (void *)(head)) \ |
291 | 23cde8bb | aliguori | (head)->cqh_first = (elm); \ |
292 | 23cde8bb | aliguori | else \
|
293 | 23cde8bb | aliguori | (head)->cqh_last->field.cqe_next = (elm); \ |
294 | 23cde8bb | aliguori | (head)->cqh_last = (elm); \ |
295 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
296 | 23cde8bb | aliguori | |
297 | 23cde8bb | aliguori | #define CIRCLEQ_REMOVE(head, elm, field) do { \ |
298 | 23cde8bb | aliguori | if ((elm)->field.cqe_next == (void *)(head)) \ |
299 | 23cde8bb | aliguori | (head)->cqh_last = (elm)->field.cqe_prev; \ |
300 | 23cde8bb | aliguori | else \
|
301 | 23cde8bb | aliguori | (elm)->field.cqe_next->field.cqe_prev = \ |
302 | 23cde8bb | aliguori | (elm)->field.cqe_prev; \ |
303 | 23cde8bb | aliguori | if ((elm)->field.cqe_prev == (void *)(head)) \ |
304 | 23cde8bb | aliguori | (head)->cqh_first = (elm)->field.cqe_next; \ |
305 | 23cde8bb | aliguori | else \
|
306 | 23cde8bb | aliguori | (elm)->field.cqe_prev->field.cqe_next = \ |
307 | 23cde8bb | aliguori | (elm)->field.cqe_next; \ |
308 | 23cde8bb | aliguori | } while (/*CONSTCOND*/0) |
309 | 23cde8bb | aliguori | |
310 | 23cde8bb | aliguori | #define CIRCLEQ_FOREACH(var, head, field) \
|
311 | 23cde8bb | aliguori | for ((var) = ((head)->cqh_first); \
|
312 | 23cde8bb | aliguori | (var) != (const void *)(head); \ |
313 | 23cde8bb | aliguori | (var) = ((var)->field.cqe_next)) |
314 | 23cde8bb | aliguori | |
315 | 23cde8bb | aliguori | #define CIRCLEQ_FOREACH_REVERSE(var, head, field) \
|
316 | 23cde8bb | aliguori | for ((var) = ((head)->cqh_last); \
|
317 | 23cde8bb | aliguori | (var) != (const void *)(head); \ |
318 | 23cde8bb | aliguori | (var) = ((var)->field.cqe_prev)) |
319 | 23cde8bb | aliguori | |
320 | 23cde8bb | aliguori | /*
|
321 | 23cde8bb | aliguori | * Circular queue access methods.
|
322 | 23cde8bb | aliguori | */
|
323 | 23cde8bb | aliguori | #define CIRCLEQ_EMPTY(head) ((head)->cqh_first == (void *)(head)) |
324 | 23cde8bb | aliguori | #define CIRCLEQ_FIRST(head) ((head)->cqh_first)
|
325 | 23cde8bb | aliguori | #define CIRCLEQ_LAST(head) ((head)->cqh_last)
|
326 | 23cde8bb | aliguori | #define CIRCLEQ_NEXT(elm, field) ((elm)->field.cqe_next)
|
327 | 23cde8bb | aliguori | #define CIRCLEQ_PREV(elm, field) ((elm)->field.cqe_prev)
|
328 | 23cde8bb | aliguori | |
329 | 23cde8bb | aliguori | #define CIRCLEQ_LOOP_NEXT(head, elm, field) \
|
330 | 23cde8bb | aliguori | (((elm)->field.cqe_next == (void *)(head)) \
|
331 | 23cde8bb | aliguori | ? ((head)->cqh_first) \ |
332 | 23cde8bb | aliguori | : (elm->field.cqe_next)) |
333 | 23cde8bb | aliguori | #define CIRCLEQ_LOOP_PREV(head, elm, field) \
|
334 | 23cde8bb | aliguori | (((elm)->field.cqe_prev == (void *)(head)) \
|
335 | 23cde8bb | aliguori | ? ((head)->cqh_last) \ |
336 | 23cde8bb | aliguori | : (elm->field.cqe_prev)) |
337 | 23cde8bb | aliguori | |
338 | 23cde8bb | aliguori | #endif /* !_SYS_QUEUE_H_ */ |