1 /* ************************************************************************
2 * Copyright 2013 Advanced Micro Devices, Inc.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 * ************************************************************************/
16
17
18 #include <stddef.h>
19 #include <list.h>
20 #include <assert.h>
21
22 static __inline
listAddAfter(ListNode * prev,ListNode * node)23 void listAddAfter(ListNode *prev, ListNode *node)
24 {
25 ListNode *next = prev->next;
26
27 prev->next = node;
28 node->prev = prev;
29 node->next = next;
30 next->prev = node;
31 }
32
33 void
listAddToTail(ListHead * head,ListNode * node)34 listAddToTail(ListHead *head, ListNode *node)
35 {
36 listAddAfter(head->prev, node);
37 }
38
39 void
listAddToHead(ListHead * head,ListNode * node)40 listAddToHead(ListHead *head, ListNode *node)
41 {
42 listAddAfter(head, node);
43 }
44
45 void
listDel(ListNode * node)46 listDel(ListNode *node)
47 {
48 #ifdef DEBUG
49 // check if it's not really the list head
50 assert(node->next != node->prev);
51 #endif
52
53 node->prev->next = node->next;
54 node->next->prev = node->prev;
55 }
56
57 ListNode
listDelFromTail(ListHead * head)58 *listDelFromTail(ListHead *head)
59 {
60 ListNode *node = head->prev;
61
62 listDel(node);
63
64 return node;
65 }
66
67 void
listDoForEach(ListHead * head,ListAction act)68 listDoForEach(ListHead *head, ListAction act)
69 {
70 ListNode *node;
71
72 for (node = listNodeFirst(head); node != head; node = node->next) {
73 act(node);
74 }
75 }
76
77 void
listDoForEachSafe(ListHead * head,ListAction act)78 listDoForEachSafe(ListHead *head, ListAction act)
79 {
80 ListNode *node, *save;
81
82 for (node = listNodeFirst(head), save = node->next; node != head;
83 node = save, save = node->next) {
84
85 act(node);
86 }
87 }
88
89 void
listDoForEachPriv(const ListHead * head,ListPrivAction act,void * actPriv)90 listDoForEachPriv(const ListHead *head, ListPrivAction act, void *actPriv)
91 {
92 ListNode *node;
93
94 for (node = listNodeFirst(head); node != head; node = node->next) {
95 act(node, actPriv);
96 }
97 }
98
99 void
listDoForEachPrivSafe(const ListHead * head,ListPrivAction act,void * actPriv)100 listDoForEachPrivSafe(const ListHead *head, ListPrivAction act, void *actPriv)
101 {
102 ListNode *node, *save;
103
104 for (node = listNodeFirst(head), save = node->next; node != head;
105 node = save, save = node->next) {
106
107 act(node, actPriv);
108 }
109 }
110
111 ListNode
listNodeSearch(const ListHead * head,const void * key,ListCmpFn cmp)112 *listNodeSearch(const ListHead *head, const void *key, ListCmpFn cmp)
113 {
114 ListNode *node;
115
116 for (node = listNodeFirst(head); node != head; node = node->next) {
117 if (!cmp(node, key)) {
118 break;
119 }
120 }
121
122 return (node == head) ? NULL : node;
123 }
124
125 size_t
listLength(const ListHead * head)126 listLength(const ListHead *head)
127 {
128 size_t length = 0;
129 ListNode *node;
130
131 for (node= listNodeFirst(head); node != head; node = node->next) {
132 length++;
133 }
134
135 return length;
136 }
137