netsniff-ng 0.5.9
[netsniff-ng.git] / staging / llist.c
blobd729e4652a9c953936f2c1ae1c667b29891919ca
1 /*
2 * Mausezahn - A fast versatile traffic generator
3 * Copyright (C) 2010 Herbert Haas
4 *
5 * This program is free software; you can redistribute it and/or modify it under
6 * the terms of the GNU General Public License version 2 as published by the
7 * Free Software Foundation.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11 * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
12 * details.
14 * You should have received a copy of the GNU General Public License along with
15 * this program; if not, see http://www.gnu.org/licenses/gpl-2.0.html
20 #include "mz.h"
21 #include "cli.h"
22 #include "mops.h"
23 #include "llist.h"
25 /* PURPOSE:
26 * General doubly linked list with management functions.
28 * NOTE:
29 * There is no dummy head element. Every element may contain data!
30 * Therefore there is only one general "create_new_element" function.
32 * You cannot delete the head element except you want to delete the whole list.
33 * Usually you delete the head element at last.
35 * head->refcount always contains the number of elements.
37 * Each element has a unique index number.
39 * The user must assign her/his data to (void*) elem->data.
41 */
44 // Create new list element - may be the first one (list==NULL)
46 struct mz_ll * mz_ll_create_new_element(struct mz_ll *list)
48 struct mz_ll *new_element;
49 new_element = (struct mz_ll*) malloc (sizeof(struct mz_ll));
50 if (new_element==NULL) return NULL;
51 _mz_ll_set_default(new_element);
52 if (list==NULL) {
53 new_element->next=new_element;
54 new_element->prev=new_element;
55 new_element->head=new_element;
56 new_element->refcount=1;
57 new_element->index=0;
58 new_element->index_last=0;
59 } else {
60 new_element->prev=list->prev;
61 new_element->next=list;
62 new_element->prev->next=new_element;
63 list->prev = new_element;
64 new_element->head=list;
65 list->refcount++;
66 list->index_last++;
67 new_element->index=list->index_last;
70 return new_element;
73 // Delete ONE list element.
74 int mz_ll_delete_element (struct mz_ll *cur)
76 if ((cur==NULL)||(cur==cur->head)) return -1; // don't delete head!
77 if (cur->data!=NULL) { free(cur->data); cur->data=NULL; }
79 if ((cur->next!=cur)&&(cur->prev!=cur)) {
80 cur->prev->next=cur->next;
81 cur->next->prev=cur->prev;
83 cur->head->refcount--;
84 if (cur!=NULL) { free(cur); cur=NULL; }
85 return 0;
89 int mz_ll_delete_list (struct mz_ll *list)
91 struct mz_ll *cur=list,
92 *tmp;
94 if (cur==NULL) return 1;
95 while (cur!=cur->next) {
96 tmp=cur->next;
97 mz_ll_delete_element(cur);
98 cur=tmp;
100 // Finally free list head:
101 if (list->data!=NULL) { free(list->data); list->data=NULL; }
102 free(list);
103 list=NULL;
104 return 0;
107 struct mz_ll * mz_ll_search_name (struct mz_ll *list, char *str)
109 struct mz_ll *cur=list;
110 do {
111 if (strncmp(cur->name, str, MZ_LL_NAME_LEN)==0) return cur;
112 cur=cur->next;
114 while (cur!=list);
115 return NULL;
118 struct mz_ll * mz_ll_search_index (struct mz_ll *list, int i)
120 struct mz_ll *cur=list;
121 do {
122 if (cur->index==i) return cur;
123 cur=cur->next;
125 while (cur!=list);
126 return NULL;
129 int mz_ll_size(struct mz_ll *list)
131 int i=0;
132 struct mz_ll *cur=list;
134 if (list==NULL) return 0;
136 do {
137 i++;
138 cur=cur->next;
140 while (cur!=list);
141 if (i!=list->refcount) fprintf(stderr, "MZ_LL_SIZE: Anomalous situation. Report this.\n");
142 return i;
146 int mz_ll_dump_all(struct mz_ll *list)
148 int i=0;
149 struct mz_ll *cur=list;
151 if (list==NULL) return 0;
153 do {
154 i++;
155 fprintf(stdout, "Element %i: '%s', index=%i\n",i,cur->name, cur->index);
156 cur=cur->next;
158 while (cur!=list);
159 return i;
164 // ------ PRIVATE: initialize list-element
165 void _mz_ll_set_default (struct mz_ll *cur)
167 cur->refcount = 0;
168 cur->data = NULL;
169 cur->name[0]='\0';
170 cur->index=0;
171 cur->state=0;