/*********************************************************
Something simplified from linux source code. this work
is done by dgod.
Use this list functions, you should support c99 or ++.
To use this, include this file.
If your compiler don't support, rewrite the micro of
foreach, if just no change to the list move the new
parameter n, else you shuld have n to define outside the
for loop and give the foreach more param
**********************************************************/
#ifndef _LIST_H_
#define _LIST_H_
typedef struct node{
struct node *prev,*next;
}node,*pnode;
#define offsetof(type,member) ((int)&(((type*)0)->member))
#define list_entry(ptr,type,member) (/
(type*)/
((char*)(ptr)-offsetof(type,member))/
)
static inline void list_init(pnode n)
{
n->prev=n->next=n;
}
static inline void __list_add(pnode n,pnode prev,pnode next)
{
next->prev=n;
prev->next=n;
n->next=next;
n->prev=prev;
}
static inline void list_add(pnode n,pnode head)
{
__list_add(n,head,head->next);
}
static inline void list_add_tail(pnode n,pnode head)
{
__list_add(n,head->prev,head);
}
static inline void __list_del(pnode prev,pnode next)
{
prev->next=next;
next->prev=prev;
}
static inline void list_del(pnode n)
{
__list_del(n->prev,n->next);
list_init(n);
}
static inline void list_move(pnode n,pnode head)
{
__list_del(n->prev,n->next);
list_add(n,head);
}
static inline void list_move_tail(pnode n,pnode head)
{
__list_del(n->prev,n->next);
list_add_tail(n,head);
}
static inline int list_empty(pnode head)
{
return head==head->next;
}
static inline void __list_splice(pnode list,pnode head)
{
node *first = list->next;
node *last = list->prev;
node *at = head->next;
first->prev = head;
head->next = first;
last->next = at;
at->prev = last;
}
static inline void list_splice(pnode list,pnode head)
{
if(!list_empty(list))
{
__list_splice(list,head);
list_init(list);
}
}
#define foreach(pos,head) /
for(node *n=pos=(head)->next;n=n->next,pos!=(head);pos=n)
#endif //_LIST_H_