#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <string.h>
struct list_head {
struct list_head *next, *prev;
};
typedef struct stu{
int no;
int addr;
char phone;
struct list_head list;
}stu;
#define POISON_POINTER_DELTA 0
#define LIST_POISON1 ((void *) 0x00100100 + POISON_POINTER_DELTA)
#define LIST_POISON2 ((void *) 0x00200200 + POISON_POINTER_DELTA)
#define list_for_each(ptr, head)\
for(ptr = (head)->next; \
ptr != (head); \
ptr = ptr->next)
#define list_for_each_safe(ptr, n, head)\
for(ptr = (head)->next, n= ptr->next; \
ptr != (head); ptr = n, n= pos->next)
#define list_entry(ptr, type, member) \
((type *)((char *)(ptr)-(unsigned long)(&((type *)0)->member)))
#define LIST_HEAD_INIT(name) { &(name), &(name) }
#define LIST_HEAD(name) \
struct list_head name = LIST_HEAD_INIT(name)
static inline void INIT_LIST_HEAD(struct list_head *list)
{
list->next = list;
list->prev = list;
}
static inline void __list_add(struct list_head *new,
struct list_head *prev,
struct list_head *next)
{
next->prev = new;
new->next = next;
new->prev = prev;
prev->next = new;
}
static inline void list_add_tail(struct list_head *new, struct list_head *head)
{
__list_add(new, head->prev, head);
}
static inline int is_empty(struct list_head *head)
{
return(head->next == head);
}
static inline void list_splice(struct list_head *head, \
struct list_head *list)
{
struct list_head *first = list->next;
struct list_head *last = list->prev;
struct list_head *pos = head->next;
first->prev = head;
head->next = first;
last->next = pos;
pos->prev = last;
}
static inline void list_split(struct list_head *head,
struct list_head *hlist,
int num_split)
{
struct list_head *pos =NULL;
struct list_head *first = NULL;
struct list_head *last = head->prev;
stu *getdat =NULL;
if(!is_empty(head)){
list_for_each(pos, head){
getdat = list_entry(pos, stu, list);
if(getdat->no == num_split){
break;
}
}
first = pos;
pos->prev->next = head;
head->prev = pos->prev;
first->prev = hlist;
hlist->next = first;
hlist->prev = last;
last->next = hlist;
}
}
static inline void _list_del(struct list_head *prev, struct list_head *next)
{
prev->next = next;
next->prev = prev;
}
static inline void list_delete(struct list_head *node, struct list_head *head)
{
if(!is_empty(head)){
_list_del(node->prev, node->next);
//free(node);
node->prev = LIST_POISON1;
node->next = LIST_POISON2;
}
}
int main(int argc, char **argv)
{
stu *dat = NULL;
struct list_head head;
struct list_head *hlist;
struct list_head *pos = NULL;
struct list_head *tmp= NULL;
int i, j;
INIT_LIST_HEAD(&head);
hlist = (struct list_head*)malloc(sizeof(struct list_head));
INIT_LIST_HEAD(hlist);
printf("list node one:\n");
for(i=0; i< 5; i++){
dat = (stu*)malloc(sizeof(stu));
if(!dat){
printf("student struct alloc failed!\n");
return -1;
}
dat->no =1+i;
dat->addr =10+i;
dat->phone = 20+i;
list_add_tail(&(dat->list), &head);
}
list_for_each(pos, &head){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
}
printf("list node2 display:\n");
for(j=0; j< 5; j++){
dat = (stu*)malloc(sizeof(stu));
if(!dat){
printf("student struct alloc failed!\n");
return -1;
}
dat->no =2+j;
dat->addr =20+j;
dat->phone = 30+j;
list_add_tail(&(dat->list), hlist);
}
list_for_each(pos, hlist){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
}
printf("list node splice:\n");
list_splice(&head, hlist);
list_for_each(pos, &head){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
}
int serch_num =6;
list_split(&head, hlist, serch_num);
printf("split list one:\n");
list_for_each(pos, &head){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
}
printf("split list two:\n");
list_for_each(pos, hlist){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
}
printf("subject free one:\n");
list_for_each_safe(pos, tmp, &head){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
list_delete(pos, &head);
free(dat);
}
printf("subject free two:\n");
list_for_each_safe(pos, tmp, hlist){
dat = list_entry(pos, stu, list);
printf("num= %d addr= %d phone= %d\n",\
dat->no, dat->addr, dat->phone);
list_delete(pos, hlist);
free(dat);
}
return 0;
}