/** * @file list.h * @brief 内核风格侵入式双向循环链表(纯头文件,C/C++ 兼容) * * 用法:将 struct list_head 嵌入你的结构体,通过 list_entry 取回宿主指针。 * 所有操作 O(1),遍历 O(n)。C++ 兼容:不用 new/class/typeof 等关键字。 */ #ifndef _LIST_H_ #define _LIST_H_ #include #ifdef __cplusplus extern "C" { #endif /* ---- 节点 ---- */ struct list_head { struct list_head *next; struct list_head *prev; }; /* ---- 初始化 ---- */ #define LIST_HEAD_INIT(n) { &(n), &(n) } #define LIST_HEAD(n) struct list_head n = LIST_HEAD_INIT(n) static inline void INIT_LIST_HEAD(struct list_head *h) { h->next = h; h->prev = h; } /* ---- 内部:在 prev 和 next 之间插入 node ---- */ static inline void __list_add(struct list_head *node, struct list_head *prev, struct list_head *next) { next->prev = node; node->next = next; node->prev = prev; prev->next = node; } /* ---- 内部:删除 prev 和 next 之间的节点 ---- */ static inline void __list_del(struct list_head *prev, struct list_head *next) { next->prev = prev; prev->next = next; } /* ---- 添加 ---- */ static inline void list_add(struct list_head *node, struct list_head *head) { __list_add(node, head, head->next); } static inline void list_add_tail(struct list_head *node, struct list_head *head) { __list_add(node, head->prev, head); } /* ---- 删除 ---- */ static inline void list_del(struct list_head *e) { __list_del(e->prev, e->next); } static inline void list_del_init(struct list_head *e) { __list_del(e->prev, e->next); INIT_LIST_HEAD(e); } /* ---- 移动 ---- */ static inline void list_move(struct list_head *l, struct list_head *h) { __list_del(l->prev, l->next); list_add(l, h); } static inline void list_move_tail(struct list_head *l, struct list_head *h) { __list_del(l->prev, l->next); list_add_tail(l, h); } /* ---- 替换 ---- */ static inline void list_replace(struct list_head *old, struct list_head *node) { node->next = old->next; node->next->prev = node; node->prev = old->prev; node->prev->next = node; } static inline void list_replace_init(struct list_head *old, struct list_head *node) { list_replace(old, node); INIT_LIST_HEAD(old); } /* ---- 判断 ---- */ static inline int list_empty(const struct list_head *h) { return h->next == h; } static inline int list_is_linked(const struct list_head *e) { return e->next != e; } /* ---- 宿主指针 ---- */ #define list_entry(ptr, type, member) \ ((type *)((char *)(ptr) - offsetof(type, member))) #define list_first_entry(h, type, member) \ list_entry((h)->next, type, member) #define list_last_entry(h, type, member) \ list_entry((h)->prev, type, member) #define list_first_entry_or_null(h, type, member) \ (list_empty(h) ? NULL : list_first_entry(h, type, member)) /* ---- 遍历 ---- */ #define list_for_each(pos, head) \ for (pos = (head)->next; pos != (head); pos = pos->next) #define list_for_each_safe(pos, n, head) \ for (pos = (head)->next, n = pos->next; pos != (head); \ pos = n, n = pos->next) #define list_for_each_entry(pos, head, member) \ for (pos = list_first_entry(head, __typeof__(*pos), member); \ &pos->member != (head); \ pos = list_entry(pos->member.next, __typeof__(*pos), member)) #define list_for_each_entry_safe(pos, n, head, member) \ for (pos = list_first_entry(head, __typeof__(*pos), member), \ n = list_entry(pos->member.next, __typeof__(*pos), member); \ &pos->member != (head); \ pos = n, \ n = list_entry(n->member.next, __typeof__(*n), member)) /* ---- 拼接 ---- */ static inline void list_splice_init(struct list_head *src, struct list_head *dst) { if (!list_empty(src)) { struct list_head *f = src->next; struct list_head *l = src->prev; struct list_head *a = dst->next; f->prev = dst; dst->next = f; l->next = a; a->prev = l; INIT_LIST_HEAD(src); } } #ifdef __cplusplus } #endif #endif