2 * Copyright (C) 1997-2005 by Objective Systems, Inc.
4 * This software is furnished under an open source license and may be
5 * used and copied only in accordance with the terms of this license.
6 * The text of the license may generally be found in the root
7 * directory of this installation in the COPYING file. It
8 * can also be viewed online at the following URL:
10 * http://www.obj-sys.com/open/license.html
12 * Any redistributions of this file including modified versions must
13 * maintain this copyright notice.
15 *****************************************************************************/
18 #include "asterisk/lock.h"
22 void dListInit (DList* pList)
26 pList->head = (DListNode*) 0;
27 pList->tail = (DListNode*) 0;
31 DListNode* dListAppend (OOCTXT* pctxt, DList* pList, void* pData)
33 DListNode* pListNode = (DListNode*)
34 memAlloc (pctxt, sizeof(DListNode));
37 pListNode->data = pData;
38 pListNode->next = (DListNode*) 0;
39 if (0 != pList->tail) {
40 pList->tail->next = pListNode;
41 pListNode->prev = pList->tail;
43 if (0 == pList->head) {
44 pList->head = pListNode;
45 pListNode->prev = (DListNode*) 0;
47 pList->tail = pListNode;
54 DListNode* dListAppendNode (OOCTXT* pctxt, DList* pList, void* pData)
56 DListNode* pListNode =
57 (DListNode*) (((char*)pData) - sizeof(DListNode));
60 pListNode->data = pData;
61 pListNode->next = (DListNode*) 0;
62 if (0 != pList->tail) {
63 pList->tail->next = pListNode;
64 pListNode->prev = pList->tail;
66 if (0 == pList->head) {
67 pList->head = pListNode;
68 pListNode->prev = (DListNode*) 0;
70 pList->tail = pListNode;
77 /* Delete the head node from the list and return the data item stored */
80 void* dListDeleteHead (OOCTXT* pctxt, DList* pList)
82 DListNode* pNode = (0 != pList) ? pList->head : 0;
84 void* pdata = pNode->data;
85 dListRemove (pList, pNode);
86 memFreePtr (pctxt, pNode);
92 /* Free all nodes, but not the data */
93 void dListFreeNodes (OOCTXT* pctxt, DList* pList)
95 DListNode* pNode, *pNextNode;
97 for (pNode = pList->head; pNode != 0; pNode = pNextNode) {
98 pNextNode = pNode->next;
99 memFreePtr (pctxt, pNode);
102 pList->head = pList->tail = 0;
105 /* Free all nodes and their data */
106 void dListFreeAll (OOCTXT* pctxt, DList* pList)
108 DListNode* pNode, *pNextNode;
110 for (pNode = pList->head; pNode != 0; pNode = pNextNode) {
111 pNextNode = pNode->next;
113 memFreePtr (pctxt, pNode->data);
114 memFreePtr (pctxt, pNode);
117 pList->head = pList->tail = 0;
120 /* Remove node from list. Node is not freed */
121 void dListRemove (DList* pList, DListNode* node)
123 if(node->next != 0) {
124 node->next->prev = node->prev;
127 pList->tail = node->prev;
129 if(node->prev != 0) {
130 node->prev->next = node->next;
133 pList->head = node->next;
138 void dListFindAndRemove(DList* pList, void *data)
140 DListNode *pNode, *pNextNode;
141 for(pNode = pList->head; pNode !=0; pNode = pNextNode){
142 pNextNode = pNode->next;
143 if(pNode->data == data) /* pointer comparison*/
147 dListRemove(pList, pNode);
150 DListNode* dListFindByIndex (DList* pList, int index)
155 if(index >= (int)pList->count) return 0;
156 for(i = 0, curNode = pList->head; i < index && curNode != 0; i++) {
157 curNode = curNode->next;
162 /* Insert item before given node */
164 DListNode* dListInsertBefore
165 (OOCTXT* pctxt, DList* pList, DListNode* node, const void* pData)
167 DListNode* pListNode = (DListNode*) memAlloc (pctxt, sizeof(DListNode));
169 if (0 != pListNode) {
170 pListNode->data = (void*)pData;
172 if (node == 0) { /* insert before end (as last element) */
173 pListNode->next = (DListNode*) 0;
174 if (0 != pList->tail) {
175 pList->tail->next = pListNode;
176 pListNode->prev = pList->tail;
178 if (0 == pList->head) {
179 pList->head = pListNode;
180 pListNode->prev = (DListNode*) 0;
182 pList->tail = pListNode;
184 else if (node == pList->head) { /* insert as head (head case) */
185 pListNode->next = pList->head;
186 pListNode->prev = (DListNode*) 0;
187 if(pList->head != 0) {
188 pList->head->prev = pListNode;
190 if(pList->tail == 0) {
191 pList->tail = pListNode;
193 pList->head = pListNode;
195 else { /* other cases */
196 pListNode->next = node;
197 pListNode->prev = node->prev;
198 node->prev = pListNode;
199 /* here, pListNode->prev always should be non-zero,
200 * because if pListNode->prev is zero - it is head case (see above).
202 pListNode->prev->next = pListNode;
211 /* Insert item after given node */
213 DListNode* dListInsertAfter
214 (OOCTXT* pctxt, DList* pList, DListNode* node, const void* pData)
216 DListNode* pListNode = (DListNode*) memAlloc (pctxt, sizeof(DListNode));
218 if (0 != pListNode) {
219 pListNode->data = (void*)pData;
221 if (node == 0) { /* insert as head (as first element) */
222 pListNode->next = pList->head;
223 pListNode->prev = (DListNode*) 0;
224 if (pList->head != 0) {
225 pList->head->prev = pListNode;
227 if (pList->tail == 0) {
228 pList->tail = pListNode;
230 pList->head = pListNode;
232 else if (node == pList->tail) { /* insert as tail (as last element) */
233 pListNode->next = (DListNode*) 0;
234 if (0 != pList->tail) {
235 pList->tail->next = pListNode;
236 pListNode->prev = pList->tail;
238 if (0 == pList->head) {
239 pList->head = pListNode;
240 pListNode->prev = (DListNode*) 0;
242 pList->tail = pListNode;
244 else { /* other cases */
245 pListNode->next = node->next;
246 pListNode->prev = node;
247 node->next = pListNode;
248 /* here, pListNode->next always should be non-zero,
249 * because if pListNode->next is zero - it is tail case (see above).
251 pListNode->next->prev = pListNode;