aboutsummaryrefslogtreecommitdiffstats
path: root/libasn1parser/asn1p_list.h
blob: 1f80878085f86f3146c6969979562d019c96cfee (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
50
51
52
53
54
55
56
57
/*
 * Singly linked tail queue support.
 */
#ifndef	ASN1_PARSER_LIST_H
#define	ASN1_PARSER_LIST_H

#define	TQ_HEAD(type)		\
	struct {		\
		type *tq_head;	\
		type**tq_tail;	\
	}

#define	TQ_HEAD_COPY(to, from)			\
	do { (to)->tq_head = (from)->tq_head;	\
	(to)->tq_tail = (from)->tq_tail; } while(0)

#define	TQ_ENTRY(type)		\
	struct {		\
		type *tq_next;	\
	}

#define TQ_FIRST(headp)		((headp)->tq_head)
#define TQ_NEXT(el, field)	((el)->field.tq_next)

#define TQ_INIT(head) do {				\
	TQ_FIRST((head)) = 0;				\
	(head)->tq_tail = &TQ_FIRST((head));		\
	} while(0)

#define	TQ_FOR(var, head, field)			\
	for((var) = TQ_FIRST((head));			\
		(var); (var) = TQ_NEXT((var), field))

#define	TQ_ADD(head, xel, field) do {			\
	typeof(xel) __el = xel;				\
	assert(TQ_NEXT((__el), field) == 0);		\
        *(head)->tq_tail = (__el);			\
        (head)->tq_tail = &TQ_NEXT((__el), field);	\
	} while(0)

/*
 * Remove the first element and return it.
 */
#define	TQ_REMOVE(head, field)	({			\
	typeof(TQ_FIRST((head))) __fel;			\
	__fel = TQ_FIRST((head));			\
	if(__fel == 0					\
	|| (TQ_FIRST((head)) = TQ_NEXT(__fel, field))	\
		== 0) {					\
		(head)->tq_tail = &TQ_FIRST((head));	\
	} else {					\
		TQ_NEXT(__fel, field) = 0;		\
	}						\
	__fel; })


#endif	/* ASN1_PARSER_LIST_H */