Line data Source code
1 : /* This file is part of GNU cflow
2 : Copyright (C) 1997, 2005, 2006, 2007, 2009, 2010 Sergey Poznyakoff
3 :
4 : GNU cflow is free software; you can redistribute it and/or modify
5 : it under the terms of the GNU General Public License as published by
6 : the Free Software Foundation; either version 3 of the License, or
7 : (at your option) any later version.
8 :
9 : GNU cflow is distributed in the hope that it will be useful,
10 : but WITHOUT ANY WARRANTY; without even the implied warranty of
11 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 : GNU General Public License for more details.
13 :
14 : You should have received a copy of the GNU General Public
15 : License along with GNU cflow; if not, write to the Free Software
16 : Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
17 : MA 02110-1301 USA */
18 :
19 : #include <cflow.h>
20 :
21 : static struct linked_list *
22 108823 : deref_linked_list (struct linked_list **plist)
23 : {
24 108823 : if (!*plist) {
25 15160 : struct linked_list *list = xmalloc(sizeof(*list));
26 15160 : list->free_data = NULL;
27 15160 : list->head = list->tail = NULL;
28 15160 : *plist = list;
29 : }
30 108823 : return *plist;
31 : }
32 :
33 :
34 : struct linked_list *
35 9884 : linked_list_create(linked_list_free_data_fp fun)
36 : {
37 9884 : struct linked_list *list = xmalloc(sizeof(*list));
38 9884 : list->free_data = fun;
39 9884 : list->head = list->tail = NULL;
40 9884 : return list;
41 : }
42 :
43 : void
44 108823 : linked_list_append(struct linked_list **plist, void *data)
45 : {
46 108823 : struct linked_list *list = deref_linked_list (plist);
47 108823 : struct linked_list_entry *entry = xmalloc(sizeof(*entry));
48 :
49 108823 : entry->list = list;
50 108823 : entry->data = data;
51 108823 : entry->next = NULL;
52 108823 : entry->prev = list->tail;
53 108823 : if (list->tail)
54 83779 : list->tail->next = entry;
55 : else
56 25044 : list->head = entry;
57 108823 : list->tail = entry;
58 108823 : }
59 :
60 : #if 0
61 : void
62 : linked_list_prepend(struct linked_list **plist, void *data)
63 : {
64 : struct linked_list *list = deref_linked_list (plist);
65 : struct linked_list_entry *entry = xmalloc(sizeof(*entry));
66 :
67 : entry->list = list;
68 : entry->data = data;
69 : if (list->head)
70 : list->head->prev = entry;
71 : entry->next = list->head;
72 : entry->prev = NULL;
73 : list->head = entry;
74 : if (!list->tail)
75 : list->tail = entry;
76 : }
77 : #endif
78 :
79 : void
80 26444 : linked_list_destroy(struct linked_list **plist)
81 : {
82 26444 : if (plist && *plist) {
83 3238 : struct linked_list *list = *plist;
84 : struct linked_list_entry *p;
85 :
86 9805 : for (p = list->head; p; ) {
87 3329 : struct linked_list_entry *next = p->next;
88 3329 : if (list->free_data)
89 3009 : list->free_data(p->data);
90 3329 : free(p);
91 3329 : p = next;
92 : }
93 3238 : free(list);
94 3238 : *plist = NULL;
95 : }
96 26444 : }
97 :
98 : void
99 7584 : linked_list_unlink(struct linked_list *list, struct linked_list_entry *ent)
100 : {
101 : struct linked_list_entry *p;
102 :
103 7584 : if ((p = ent->prev))
104 830 : p->next = ent->next;
105 : else
106 6754 : list->head = ent->next;
107 :
108 7584 : if ((p = ent->next))
109 3966 : p->prev = ent->prev;
110 : else
111 3618 : list->tail = ent->prev;
112 7584 : if (list->free_data)
113 0 : list->free_data(ent->data);
114 7584 : free(ent);
115 7584 : }
116 :
117 : void
118 28957 : linked_list_iterate(struct linked_list **plist,
119 : int (*itr) (void *, void *), void *data)
120 : {
121 : struct linked_list *list;
122 : struct linked_list_entry *p;
123 :
124 28957 : if (!*plist)
125 38090 : return;
126 19824 : list = *plist;
127 277765 : for (p = linked_list_head(list); p; ) {
128 238117 : struct linked_list_entry *next = p->next;
129 :
130 238117 : if (itr(p->data, data))
131 7472 : linked_list_unlink(list, p);
132 238117 : p = next;
133 : }
134 19824 : if (!list->head)
135 2981 : linked_list_destroy(&list);
136 19824 : *plist = list;
137 : }
138 :
139 : int
140 92217 : data_in_list(void *data, struct linked_list *list)
141 : {
142 : struct linked_list_entry *p;
143 :
144 614414 : for (p = linked_list_head(list); p; p = p->next)
145 559081 : if (p->data == data)
146 36884 : return 1;
147 55333 : return 0;
148 : }
|