3 * libEtPan! -- a mail stuff library
5 * clist - Implements simple generic double-linked pointer lists
7 * Copyright (c) 1999-2000, Gaƫl Roualland <gael.roualland@iname.com>
8 * interface changes - 2002 - DINH Viet Hoa
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in the
18 * documentation and/or other materials provided with the distribution.
19 * 3. Neither the name of the libEtPan! project nor the names of its
20 * contributors may be used to endorse or promote products derived
21 * from this software without specific prior written permission.
23 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
48 lst
= (clist
*) malloc(sizeof(clist
));
49 if (!lst
) return NULL
;
51 lst
->first
= lst
->last
= NULL
;
57 void clist_free(clist
* lst
) {
71 int clist_isempty(clist
* lst
) {
72 return ((lst
->first
==lst
->last
) && (lst
->last
==NULL
));
75 clistiter
* clist_begin(clist
* lst
) {
79 clistiter
* clist_end(clist
* lst
) {
83 clistiter
* clist_next(clistiter
* iter
) {
90 clistiter
* clist_previous(clistiter
* iter
) {
92 return iter
->previous
;
97 void * clist_content(clistiter
* iter
) {
104 int clist_count(clist
* lst
) {
108 int clist_prepend(clist
* lst
, void * data
) {
109 return clist_insert_before(lst
, lst
->first
, data
);
112 int clist_append(clist
* lst
, void * data
) {
113 return clist_insert_after(lst
, lst
->last
, data
);
117 int clist_insert_before(clist
* lst
, clistiter
* iter
, void * data
) {
120 c
= (clistcell
*) malloc(sizeof(clistcell
));
126 if (clist_isempty(lst
)) {
127 c
->previous
= c
->next
= NULL
;
128 lst
->first
= lst
->last
= c
;
133 c
->previous
= lst
->last
;
134 c
->previous
->next
= c
;
140 c
->previous
= iter
->previous
;
142 c
->next
->previous
= c
;
144 c
->previous
->next
= c
;
151 int clist_insert_after(clist
* lst
, clistiter
* iter
, void * data
) {
154 c
= (clistcell
*) malloc(sizeof(clistcell
));
160 if (clist_isempty(lst
)) {
161 c
->previous
= c
->next
= NULL
;
162 lst
->first
= lst
->last
= c
;
167 c
->previous
= lst
->last
;
168 c
->previous
->next
= c
;
175 c
->next
= iter
->next
;
177 c
->next
->previous
= c
;
180 c
->previous
->next
= c
;
185 clistiter
* clist_delete(clist
* lst
, clistiter
* iter
) {
188 if (!iter
) return NULL
;
191 iter
->previous
->next
= iter
->next
;
193 lst
->first
= iter
->next
;
196 iter
->next
->previous
= iter
->previous
;
199 lst
->last
= iter
->previous
;
211 void clist_foreach(clist
* lst
, clist_func func
, void * data
)
215 for(cur
= clist_begin(lst
) ; cur
!= NULL
; cur
= cur
->next
)
216 func(cur
->data
, data
);
219 void clist_concat(clist
* dest
, clist
* src
)
221 if (src
->first
== NULL
) {
224 else if (dest
->last
== NULL
) {
225 dest
->first
= src
->first
;
226 dest
->last
= src
->last
;
229 dest
->last
->next
= src
->first
;
230 src
->first
->previous
= dest
->last
;
231 dest
->last
= src
->last
;
234 dest
->count
+= src
->count
;
235 src
->last
= src
->first
= NULL
;
238 static inline clistiter
* internal_clist_nth(clist
* lst
, int index
)
242 cur
= clist_begin(lst
);
243 while ((index
> 0) && (cur
!= NULL
)) {
254 void * clist_nth_data(clist
* lst
, int index
)
258 cur
= internal_clist_nth(lst
, index
);
265 clistiter
* clist_nth(clist
* lst
, int index
)
267 return internal_clist_nth(lst
, index
);