summaryrefslogtreecommitdiff
path: root/libqueue/queue/stq.h
blob: dcf5c8537b1de90cd5fd81792976f0c4fccdf185 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
/* vim: set ts=4 sw=4 ai:
 * stq.h -- singly linked tail queue implementation derived from NetBSD's queue.h
 */

#ifndef STQ_H
#define STQ_H

struct stqe {
	void *data;
	struct stqe *next;
};

struct stqh {
	struct stqe *first;
	struct stqe **last;
};

#define stq_first(hd) ((hd)->first)
#define stq_last(hd) (*(((struct stqh *)(void *)((hd)->last))->last))
#define stq_next(e) ((e)->next)
#define stq_empty(hd) (((hd)->first) == NULL)
#define stq_init(hd) do { \
	(hd)->first = NULL; \
	(hd)->last = &(hd)->first; \
} while (0)


#define stq_foreach(var,head) \
	for ((var) = stq_first((head)); \
		(var); \
		(var) = stq_next((var)))

#define stq_foreach_safe(var,head,vnext) \
	for ((var) = stq_first((head)); \
		(var) && ((vnext) = stq_next((var)),1); \
		(var) = (vnext))

struct stqh *stq_new(void);
struct stqe *stq_elem_new(void *);
void stq_insert_head(struct stqh *, struct stqe *);
void stq_insert_tail(struct stqh *, struct stqe *);
void stq_insert_after(struct stqh *, struct stqe *, struct stqe *);
void stq_remove_head(struct stqh *);
void stq_remove(struct stqh *, struct stqe *);
void stq_concat(struct stqh *, struct stqh *);
void stq_cleanup(struct stqh *, void (*)(void *));
struct stqe *stq_find_from_data(struct stqh *, const void *, int (*)(const void *, const void *));

#endif/*!STQ_H*/