list.h

Go to the documentation of this file.
00001 // Copyright 2006 Benedikt Böhm <hollow@gentoo.org>
00002 //
00003 // This program is free software; you can redistribute it and/or modify
00004 // it under the terms of the GNU General Public License as published by
00005 // the Free Software Foundation; either version 2 of the License, or
00006 // (at your option) any later version.
00007 //
00008 // This program is distributed in the hope that it will be useful,
00009 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00010 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00011 // GNU General Public License for more details.
00012 //
00013 // You should have received a copy of the GNU General Public License
00014 // along with this program; if not, write to the
00015 // Free Software Foundation, Inc.,
00016 // 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
00017 
00018 /*!
00019  * @defgroup list Simple doubly linked lists
00020  *
00021  * The simplest kind of linked list is a singly-linked list, which has one link
00022  * per node. This link points to the next node in the list, or to a null value
00023  * or empty list if it is the final node; e.g. 12 -> 99 -> 37 -> NULL.
00024  *
00025  * A more sophisticated kind of linked list is a doubly-linked list. Each node
00026  * has two links: one points to the previous node, or points to a null value or
00027  * empty list if it is the first node; and one points to the next, or points to
00028  * a null value or empty list if it is the final node; e.g.
00029  * NULL <- 26 <-> 56 <-> 46 -> NULL.
00030  *
00031  * The list family of functions and macros provide routines to create a list,
00032  * add, move or remove elements and iterate over the list.
00033  *
00034  * @{
00035  */
00036 
00037 #ifndef _LUCID_LIST_H
00038 #define _LUCID_LIST_H
00039 
00040 #include <stddef.h>
00041 
00042 /*! @brief get container of list head */
00043 #define container_of(ptr, type, member) \
00044         ((type *)((char *)(ptr) - offsetof(type, member)))
00045 
00046 /*
00047  * Simple doubly linked list implementation.
00048  *
00049  * Some of the internal functions ("__xxx") are useful when
00050  * manipulating whole lists rather than single entries, as
00051  * sometimes we already know the next/prev entries and we can
00052  * generate better code by using them directly rather than
00053  * using the generic single-entry routines.
00054  */
00055 
00056 /*! @brief list head */
00057 struct list_head {
00058         struct list_head *next, *prev;
00059 };
00060 
00061 /*! @brief list head initialization */
00062 #define LIST_HEAD_INIT(name) { &(name), &(name) }
00063 
00064 /*! @brief list head creation */
00065 #define LIST_HEAD(name) \
00066         struct list_head name = LIST_HEAD_INIT(name)
00067 
00068 static inline void INIT_LIST_HEAD(struct list_head *list)
00069 {
00070         list->next = list;
00071         list->prev = list;
00072 }
00073 
00074 /*
00075  * Insert a new entry between two known consecutive entries.
00076  *
00077  * This is only for internal list manipulation where we know
00078  * the prev/next entries already!
00079  */
00080 static inline
00081 void __list_add(struct list_head *new,
00082                 struct list_head *prev,
00083                 struct list_head *next)
00084 {
00085         next->prev = new;
00086         new->next = next;
00087         new->prev = prev;
00088         prev->next = new;
00089 }
00090 
00091 /*!
00092  * @brief add a new entry
00093  *
00094  * Insert a new entry after the specified head.
00095  * This is good for implementing stacks.
00096  *
00097  * @param new  new entry to be added
00098  * @param head list head to add it after
00099  */
00100 static inline
00101 void list_add(struct list_head *new, struct list_head *head)
00102 {
00103         __list_add(new, head, head->next);
00104 }
00105 
00106 /*!
00107  * @brief add a new entry
00108  *
00109  * Insert a new entry before the specified head.
00110  * This is useful for implementing queues.
00111  *
00112  * @param new  new entry to be added
00113  * @param head list head to add it before
00114  */
00115 static inline
00116 void list_add_tail(struct list_head *new, struct list_head *head)
00117 {
00118         __list_add(new, head->prev, head);
00119 }
00120 
00121 /*
00122  * Delete a list entry by making the prev/next entries
00123  * point to each other.
00124  *
00125  * This is only for internal list manipulation where we know
00126  * the prev/next entries already!
00127  */
00128 static inline
00129 void __list_del(struct list_head * prev, struct list_head * next)
00130 {
00131         next->prev = prev;
00132         prev->next = next;
00133 }
00134 
00135 /*!
00136  * @brief deletes entry from list
00137  *
00138  * @param entry the element to delete from the list
00139  *
00140  * @note list_empty on entry does not return true after this, the entry is
00141  *       in an undefined state
00142  */
00143 static inline
00144 void list_del(struct list_head *entry)
00145 {
00146         __list_del(entry->prev, entry->next);
00147         entry->next = (void *) 0;
00148         entry->prev = (void *) 0;
00149 }
00150 
00151 /*!
00152  * @brief deletes entry from list and reinitialize it
00153  *
00154  * @param entry the element to delete from the list
00155  */
00156 static inline
00157 void list_del_init(struct list_head *entry)
00158 {
00159         __list_del(entry->prev, entry->next);
00160         INIT_LIST_HEAD(entry);
00161 }
00162 
00163 /*!
00164  * @brief delete from one list and add as another's head
00165  *
00166  * @param list the entry to move
00167  * @param head the head that will precede our entry
00168  */
00169 static inline
00170 void list_move(struct list_head *list, struct list_head *head)
00171 {
00172         __list_del(list->prev, list->next);
00173         list_add(list, head);
00174 }
00175 
00176 /*!
00177  * @brief delete from one list and add as another's tail
00178  *
00179  * @param list the entry to move
00180  * @param head the head that will follow our entry
00181  */
00182 static inline
00183 void list_move_tail(struct list_head *list, struct list_head *head)
00184 {
00185         __list_del(list->prev, list->next);
00186         list_add_tail(list, head);
00187 }
00188 
00189 /*!
00190  * @brief tests whether a list is empty
00191  *
00192  * @param head the list to test
00193  */
00194 static inline
00195 int list_empty(const struct list_head *head)
00196 {
00197         return head->next == head;
00198 }
00199 
00200 static inline
00201 void __list_splice(struct list_head *list, struct list_head *head)
00202 {
00203         struct list_head *first = list->next;
00204         struct list_head *last = list->prev;
00205         struct list_head *at = head->next;
00206         
00207         first->prev = head;
00208         head->next = first;
00209         
00210         last->next = at;
00211         at->prev = last;
00212 }
00213 
00214 /*!
00215  * @brief join two lists
00216  *
00217  * @param list the new list to add
00218  * @param head the place to add it in the first list
00219  */
00220 static inline
00221 void list_splice(struct list_head *list, struct list_head *head)
00222 {
00223         if (!list_empty(list))
00224                 __list_splice(list, head);
00225 }
00226 
00227 /*!
00228  * @brief join two lists and reinitialise the emptied list
00229  *
00230  * @param list the new list to add
00231  * @param head the place to add it in the first list
00232  */
00233 static inline
00234 void list_splice_init(struct list_head *list, struct list_head *head)
00235 {
00236         if (!list_empty(list)) {
00237                 __list_splice(list, head);
00238                 INIT_LIST_HEAD(list);
00239         }
00240 }
00241 
00242 /*!
00243  * @brief get the struct for this entry
00244  *
00245  * @param ptr    the &struct list_head pointer
00246  * @param type   the type of the struct this is embedded in
00247  * @param member the name of the list_struct within the struct
00248  */
00249 #define list_entry(ptr, type, member) \
00250         container_of(ptr, type, member)
00251 
00252 /*!
00253  * @brief iterate over a list
00254  *
00255  * @param pos  the &struct list_head to use as a loop counter
00256  * @param head the head for your list
00257  */
00258 #define list_for_each(pos, head) \
00259         for (pos = (head)->next; pos != (head); pos = pos->next)
00260 
00261 /*!
00262  * @brief iterate over a list backwards
00263  *
00264  * @param pos  the &struct list_head to use as a loop counter
00265  * @param head the head for your list
00266  */
00267 #define list_for_each_prev(pos, head) \
00268         for (pos = (head)->prev; pos != (head); pos = pos->prev)
00269 
00270 /*!
00271  * @brief iterate over a list safe against removal of list entry
00272  *
00273  * @param pos   the &struct list_head to use as a loop counter
00274  * @param n     another &struct list_head to use as temporary storage
00275  * @param head  the head for your list
00276  */
00277 #define list_for_each_safe(pos, n, head) \
00278         for (pos = (head)->next, n = pos->next; pos != (head); \
00279                 pos = n, n = pos->next)
00280 
00281 /*!
00282  * @brief iterate over list of given type
00283  *
00284  * @param pos    the type * to use as a loop counter
00285  * @param head:  the head for your list
00286  * @param member the name of the list_struct within the struct
00287  */
00288 #define list_for_each_entry(pos, head, member) \
00289         for (pos = list_entry((head)->next, typeof(*pos), member); \
00290              &pos->member != (head); \
00291              pos = list_entry(pos->member.next, typeof(*pos), member))
00292 
00293 /*!
00294  * @brief iterate backwards over list of given type.
00295  *
00296  * @param pos    the type * to use as a loop counter
00297  * @param head   the head for your list
00298  * @param member the name of the list_struct within the struct
00299  */
00300 #define list_for_each_entry_reverse(pos, head, member) \
00301         for (pos = list_entry((head)->prev, typeof(*pos), member); \
00302              &pos->member != (head); \
00303              pos = list_entry(pos->member.prev, typeof(*pos), member))
00304 
00305 /*!
00306  * @brief iterate over list of given type safe against removal of list entry
00307  *
00308  * @param pos    the type * to use as a loop counter
00309  * @param n      another type * to use as temporary storage
00310  * @param head   the head for your list
00311  * @param member the name of the list_struct within the struct
00312  */
00313 #define list_for_each_entry_safe(pos, n, head, member) \
00314         for (pos = list_entry((head)->next, typeof(*pos), member), \
00315              n = list_entry(pos->member.next, typeof(*pos), member); \
00316              &pos->member != (head); \
00317              pos = n, n = list_entry(n->member.next, typeof(*n), member))
00318 
00319 /*!
00320  * @brief iterate backwards over list of given type safe against removal of list entry
00321  *
00322  * @param pos    the type * to use as a loop counter
00323  * @param n      another type * to use as temporary storage
00324  * @param head   the head for your list
00325  * @param member the name of the list_struct within the struct
00326  */
00327 #define list_for_each_entry_safe_reverse(pos, n, head, member) \
00328         for (pos = list_entry((head)->prev, typeof(*pos), member), \
00329              n = list_entry(pos->member.prev, typeof(*pos), member); \
00330              &pos->member != (head); \
00331              pos = n, n = list_entry(n->member.prev, typeof(*n), member))
00332 
00333 #endif
00334 
00335 /*! @} list */

Generated on Sun Dec 3 17:45:53 2006 for lucid by  doxygen 1.5.1