2 * Copyright(c) 2002-2011 Exar Corp.
5 * Redistribution and use in source and binary forms, with or without
6 * modification are permitted provided the following conditions are met:
8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
15 * 3. Neither the name of the Exar Corporation nor the names of its
16 * contributors may be used to endorse or promote products derived from
17 * this software without specific prior written permission.
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
39 * struct vxge_list_t - List item.
40 * @prev: Previous list item.
41 * @next: Next list item.
43 * Item of a bi-directional linked list.
45 typedef struct vxge_list_t {
46 struct vxge_list_t *prev;
47 struct vxge_list_t *next;
51 * vxge_list_init - Initialize linked list.
52 * @header: first element of the list (head)
54 * Initialize linked list.
55 * See also: vxge_list_t {}.
57 static inline void vxge_list_init(vxge_list_t *header)
59 vxge_assert(header != NULL);
61 header->next = header;
62 header->prev = header;
66 * vxge_list_is_empty - Is the list empty?
67 * @header: first element of the list (head)
69 * Determine whether the bi-directional list is empty. Return '1' in
71 * See also: vxge_list_t {}.
73 static inline int vxge_list_is_empty(vxge_list_t *header)
75 vxge_assert(header != NULL);
77 return (header->next == header);
81 * vxge_list_first_get - Return the first item from the linked list.
82 * @header: first element of the list (head)
84 * Returns the next item from the header.
85 * Returns NULL if the next item is header itself
86 * See also: vxge_list_remove(), vxge_list_insert(), vxge_list_t {}.
88 static inline vxge_list_t *vxge_list_first_get(vxge_list_t *header)
90 vxge_assert(header != NULL);
91 vxge_assert(header->next != NULL);
92 vxge_assert(header->prev != NULL);
94 if (header->next == header)
97 return (header->next);
101 * vxge_list_remove - Remove the specified item from the linked list.
102 * @item: element of the list
104 * Remove item from a list.
105 * See also: vxge_list_insert(), vxge_list_t {}.
107 static inline void vxge_list_remove(vxge_list_t *item)
109 vxge_assert(item != NULL);
110 vxge_assert(item->next != NULL);
111 vxge_assert(item->prev != NULL);
113 item->next->prev = item->prev;
114 item->prev->next = item->next;
115 #if defined(VXGE_DEBUG_ASSERT)
116 item->next = item->prev = NULL;
121 * vxge_list_insert - Insert a new item after the specified item.
122 * @new_item: new element of the list
123 * @prev_item: element of the list after which the new element is
126 * Insert new item (new_item) after given item (prev_item).
127 * See also: vxge_list_remove(), vxge_list_insert_before(), vxge_list_t {}.
129 static inline void vxge_list_insert(vxge_list_t *new_item,
130 vxge_list_t *prev_item)
132 vxge_assert(new_item != NULL);
133 vxge_assert(prev_item != NULL);
134 vxge_assert(prev_item->next != NULL);
136 new_item->next = prev_item->next;
137 new_item->prev = prev_item;
138 prev_item->next->prev = new_item;
139 prev_item->next = new_item;
143 * vxge_list_insert_before - Insert a new item before the specified item.
144 * @new_item: new element of the list
145 * @next_item: element of the list after which the new element is inserted
147 * Insert new item (new_item) before given item (next_item).
149 static inline void vxge_list_insert_before(vxge_list_t *new_item,
150 vxge_list_t * next_item)
152 vxge_assert(new_item != NULL);
153 vxge_assert(next_item != NULL);
154 vxge_assert(next_item->next != NULL);
156 new_item->next = next_item;
157 new_item->prev = next_item->prev;
158 next_item->prev->next = new_item;
159 next_item->prev = new_item;
162 #define vxge_list_for_each(_p, _h) \
163 for (_p = (_h)->next, vxge_os_prefetch(_p->next); _p != (_h); \
164 _p = _p->next, vxge_os_prefetch(_p->next))
166 #define vxge_list_for_each_safe(_p, _n, _h) \
167 for (_p = (_h)->next, _n = _p->next; _p != (_h); \
168 _p = _n, _n = _p->next)
170 #define vxge_list_for_each_prev_safe(_p, _n, _h) \
171 for (_p = (_h)->prev, _n = _p->prev; _p != (_h); \
172 _p = _n, _n = _p->prev)
174 #if defined(__GNUC__)
176 * vxge_container_of - Given a member, return the containing structure.
177 * @ptr: the pointer to the member.
178 * @type: the type of the container struct this is embedded in.
179 * @member: the name of the member within the struct.
181 * Cast a member of a structure out to the containing structure.
183 #define vxge_container_of(ptr, type, member) (\
184 { __typeof(((type *)0)->member) *__mptr = (ptr); \
185 (type *)(void *)((char *)__mptr - ((ptr_t)&((type *)0)->member)); })
187 /* type unsafe version */
188 #define vxge_container_of(ptr, type, member) \
189 ((type *)(void *)((char *)(ptr) - ((ptr_t)&((type *)0)->member)))
193 * vxge_offsetof - Offset of the member in the containing structure.
195 * @m: the name of the member within the struct.
197 * Return the offset of the member @m in the structure @t.
199 #define vxge_offsetof(t, m) ((ptr_t)(&((t *)0)->m))
203 #endif /* VXGE_LIST_H */