mdblist.h

Go to the documentation of this file.
00001 
00028 #ifndef _NCS_DBLIST_H
00029 #define _NCS_DBLIST_H
00030 
00031 #ifdef __cplusplus
00032 extern "C" {
00033 #endif
00034 
00045 struct list_head {
00046     struct list_head *next, *prev;
00047 };
00048 
00053 typedef struct list_head list_t;
00054 
00055 #define LIST_HEAD_INIT(name) { &(name), &(name) }
00056 
00057 /* define and init a list head */
00058 #define LIST_HEAD(name) \
00059     struct list_head name = LIST_HEAD_INIT(name)
00060 
00061 /* init a list head */
00062 #define INIT_LIST_HEAD(ptr) do { \
00063     (ptr)->next = (ptr); (ptr)->prev = (ptr); \
00064 } while (0)
00065 
00066 /*
00067  * \fn void __list_add(struct list_head * _new, \
00068                 struct list_head * prev, \
00069                 struct list_head * next)
00070  * \brief Insert a _new entry between two known consecutive entries. 
00071  *
00072  * This is only for internal list manipulation where we know
00073  * the prev/next entries already!
00074  */
00075 static inline void __list_add(struct list_head * _new,
00076     struct list_head * prev,
00077     struct list_head * next)
00078 {
00079     next->prev = _new;
00080     _new->next = next;
00081     _new->prev = prev;
00082     prev->next = _new;
00083 }
00084 
00095 static inline void list_add(struct list_head *_new, struct list_head *head)
00096 {
00097     __list_add(_new, head, head->next);
00098 }
00099 
00110 static inline void list_add_tail(struct list_head *_new, struct list_head *head)
00111 {
00112     __list_add(_new, head->prev, head);
00113 }
00114 
00115 /*
00116  * \fn  void __list_del(struct list_head * prev, \
00117                   struct list_head * next)
00118  * \brief Delete a list entry by making the prev/next entries
00119  * point to each other.
00120  *
00121  * This is only for internal list manipulation where we know
00122  * the prev/next entries already!
00123  */
00124 static inline void __list_del(struct list_head * prev,
00125                   struct list_head * next)
00126 {
00127     next->prev = prev;
00128     prev->next = next;
00129 }
00130 
00136 static inline void list_del(struct list_head *entry)
00137 {
00138     __list_del(entry->prev, entry->next);
00139 }
00140 
00147 static inline void list_del_init(struct list_head *entry)
00148 {
00149     __list_del(entry->prev, entry->next);
00150     INIT_LIST_HEAD(entry); 
00151 }
00152 
00159 static inline int list_empty(struct list_head *head)
00160 {
00161     return head->next == head;
00162 }
00163 
00172 #define list_entry(ptr, type, member) \
00173     ((type *)((char *)(ptr)-(unsigned long)(&((type *)0)->member)))
00174 
00181 #define list_for_each(pos, head) \
00182     for (pos = (head)->next; pos != (head); pos = pos->next)
00183             
00191 #define list_for_each_safe(pos, n, head) \
00192     for (pos = (head)->next, n = pos->next; pos != (head); \
00193         pos = n, n = pos->next)
00194 
00202 #define list_for_each_ex(pos, head, begin) \
00203     for (pos = (begin)->next; pos != (head); pos = (pos)->next)
00204 
00214 #define list_for_index(pos, i, head, index) \
00215     for (pos = (head)->next, i=0; (pos != (head) && i < index); pos = pos->next,i++)
00216 
00217 
00218 static inline int list_add_by_index(struct list_head *_new, struct list_head *head, int index)
00219 {
00220     list_t *pos = head;
00221     int i = -1;
00222 
00223     if (index >= 0) {
00224         for (pos = (head)->next, i=0; (pos != (head) && i < index); pos = pos->next,i++);
00225     }
00226     list_add_tail (_new, pos);
00227     return i;
00228 }
00229 
00230 
00231 /* added for normal list operations */
00232 #define GETBY_EX(func, head, entrytype, member, datatype, ret, equal_cond) \
00233         void* func (datatype data) \
00234         { \
00235             list_t *me; \
00236             entrytype *pdata; \
00237             int i = 0; \
00238             \
00239             list_for_each(me, head) { \
00240                 pdata = list_entry(me, entrytype, member); \
00241                 if (equal_cond) \
00242                     return ret; \
00243             } \
00244             return NULL; \
00245         }
00246 
00247 #define GET_LIST_BY_DATA(func, head, entrytype, member, datamember, datatype) \
00248         GETBY_EX(func, head, entrytype, member, datatype, me, (pdata->datamember == data))
00249 
00250 #define GET_ENTRY_BY_DATA(func, head, entrytype, member, datamember, datatype) \
00251         GETBY_EX(func, head, entrytype, member, datatype, pdata, (pdata->datamember == data))
00252 
00253 /* for string */
00254 #define GET_LIST_BY_STRING(func, head, entrytype, member, datamember, datatype) \
00255         GETBY_EX(func, head, entrytype, member, datatype, me, (strcmp(pdata->datamember,data)==0))
00256 
00257 #define GET_ENTRY_BY_STRING(func, head, entrytype, member, datamember, datatype) \
00258         GETBY_EX(func, head, entrytype, member, datatype, pdata, (strcmp(pdata->datamember,data)==0))
00259 
00260 /* for index */
00261 #define GET_ENTRY_BY_INDEX(func, entrytype, member) \
00262         static inline entrytype* func (list_t *head, int index) \
00263         { \
00264             list_t *me; \
00265             int i = 0; \
00266             \
00267             list_for_each(me, head) { \
00268                 if (i++ == index) \
00269                     return list_entry(me, entrytype, member); \
00270             } \
00271             return NULL; \
00272         }
00273 
00274 #define GET_ENTRY_INDEX(func, entrytype, member) \
00275         static inline int func (list_t *head, entrytype* entry) \
00276         { \
00277             list_t *me; \
00278             int i = 0; \
00279             \
00280             list_for_each(me, head) { \
00281                 if (entry == list_entry(me, entrytype, member)) \
00282                     return i; \
00283                 i++; \
00284             } \
00285             return -1; \
00286         }
00287 
00288 #ifdef __cplusplus
00289 }
00290 #endif
00291 
00292 #endif /* _NCS_DBLIST_H */
Generated on Fri Jun 10 11:18:06 2011 for New Control Set V1.0.0 API Reference by  doxygen 1.6.3