• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 HiSilicon (Shanghai) Technologies CO., LIMITED.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17  */
18 #ifndef __HI_LIST_H__
19 #define __HI_LIST_H__
20 
21 #include <hi_types_base.h>
22 
23 /* ************************************************************************** */
24 HI_START_HEADER
25 
26 /*
27  * 备注:本文件对链表接口重新命名,使用LTOS接口重新实现。
28  */
29 typedef struct hi_list {
30     struct hi_list *prev;
31     struct hi_list *next;
32 } hi_list;
33 
34 /*
35 功能描述:
36     初始化头节点,注意此节点仅用于管理,不是用户输入的数据节点
37  */
hi_list_init(hi_list * list)38 static inline hi_void hi_list_init(hi_list *list)
39 {
40     list->next = list;
41     list->prev = list;
42 }
43 
44 /*
45 功能描述:
46     把node插入为list的第一个节点
47  */
hi_list_head_insert(hi_list * node,hi_list * list)48 static inline hi_void hi_list_head_insert(hi_list *node, hi_list *list)
49 {
50     node->next = list->next;
51     node->prev = list;
52     list->next->prev = node;
53     list->next = node;
54 }
55 
56 /*
57 功能描述:
58     把node插入为list的第一个节点
59  */
hi_list_head_insert_optimize(hi_list * node,hi_list * list)60 __attribute__((always_inline)) static inline hi_void hi_list_head_insert_optimize(hi_list *node, hi_list *list)
61 {
62     node->next = list->next;
63     node->prev = list;
64     list->next->prev = node;
65     list->next = node;
66 }
67 
68 /*
69 功能描述:
70     把node插入为list的最后一个节点
71  */
hi_list_tail_insert(hi_list * node,hi_list * list)72 static inline hi_void hi_list_tail_insert(hi_list *node, hi_list *list)
73 {
74     hi_list_head_insert(node, list->prev);
75 }
76 
77 /*
78 功能描述:
79     把node插入为list的最后一个节点
80  */
hi_list_tail_insert_optimize(hi_list * node,hi_list * list)81 __attribute__((always_inline)) static inline hi_void hi_list_tail_insert_optimize(hi_list *node, hi_list *list)
82 {
83     hi_list_head_insert_optimize(node, list->prev);
84 }
85 
86 /*
87 功能描述:
88     从链表中删除某个节点
89  */
hi_list_delete(hi_list * node)90 static inline hi_void hi_list_delete(hi_list *node)
91 {
92     if (node->next == HI_NULL || node->prev == HI_NULL) {
93         return;
94     }
95 
96     node->next->prev = node->prev;
97     node->prev->next = node->next;
98     node->next = (hi_list *)HI_NULL;
99     node->prev = (hi_list *)HI_NULL;
100 }
101 
102 /*
103 功能描述:
104     从链表中删除某个节点
105  */
hi_list_delete_optimize(hi_list * node)106 __attribute__((always_inline)) static inline hi_void hi_list_delete_optimize(hi_list *node)
107 {
108     if (node->next == HI_NULL || node->prev == HI_NULL) {
109         return;
110     }
111 
112     node->next->prev = node->prev;
113     node->prev->next = node->next;
114     node->next = (hi_list *)HI_NULL;
115     node->prev = (hi_list *)HI_NULL;
116 }
117 
118 /*
119 功能描述:
120     删除链表的第一个节点,不释放相关内存
121  */
hi_list_delete_head(hi_list * list)122 static inline hi_list *hi_list_delete_head(hi_list *list)
123 {
124     hi_list *del_node;
125 
126     del_node = list->next;
127     if (del_node == list || del_node == HI_NULL) {
128         return HI_NULL;
129     }
130 
131     hi_list_delete(del_node);
132     return del_node;
133 }
134 
135 /*
136 功能描述:
137     删除链表的第一个节点,不释放相关内存
138  */
hi_list_delete_head_optimize(hi_list * list)139 __attribute__((always_inline)) static inline hi_list *hi_list_delete_head_optimize(hi_list *list)
140 {
141     hi_list *del_node;
142 
143     del_node = list->next;
144     if (del_node == list || del_node == HI_NULL) {
145         return HI_NULL;
146     }
147 
148     hi_list_delete_optimize(del_node);
149     return del_node;
150 }
151 
152 /*
153 功能描述:
154     删除链表尾部节点,不释放相关内存
155  */
hi_list_delete_tail(hi_list * list)156 static inline hi_list *hi_list_delete_tail(hi_list *list)
157 {
158     hi_list *del_node;
159 
160     del_node = list->prev;
161     if (del_node == list || del_node == HI_NULL) {
162         return HI_NULL;
163     }
164 
165     hi_list_delete(del_node);
166     return del_node;
167 }
168 
169 /*
170 功能描述:
171     判断链表是否为空
172  */
hi_is_list_empty(hi_list * list)173 static inline hi_bool hi_is_list_empty(hi_list *list)
174 {
175     if (list->next == HI_NULL || list->prev == HI_NULL) {
176         return HI_TRUE;
177     }
178     return (hi_bool)(list->next == list);
179 }
180 
hi_is_list_empty_optimize(hi_list * list)181 __attribute__((always_inline)) static inline hi_bool hi_is_list_empty_optimize(hi_list *list)
182 {
183     if (list->next == HI_NULL || list->prev == HI_NULL) {
184         return HI_TRUE;
185     }
186     return (hi_bool)(list->next == list);
187 }
188 
189 
190 /*
191 功能描述:
192     去初始化链表,管理节点清空,其他成员节点首尾相连仍然是一个双向链表。
193  */
hi_list_del_init(hi_list * list)194 static inline hi_void hi_list_del_init(hi_list *list)
195 {
196     list->next->prev = list->prev;
197     list->prev->next = list->next;
198 
199     list->next = list;
200     list->prev = list;
201 }
202 
203 /*
204 功能描述:
205     将链表2加入链表1的尾部
206  */
hi_list_join_tail(hi_list * list1,hi_list * list2)207 static inline hi_void hi_list_join_tail(hi_list *list1, hi_list *list2)
208 {
209     list1->prev->next = list2->next;
210     list2->next->prev = list1->prev;
211     list2->prev->next = list1;
212     list1->prev = list2->prev;
213 }
214 
215 /*
216 功能描述:
217     将链表2加入链表1的头部
218  */
hi_list_join_head(hi_list * list1,hi_list * list2)219 static inline hi_void hi_list_join_head(hi_list *list1, hi_list *list2)
220 {
221     /* list2 is empty. */
222     if (list2->next == list2) {
223         return;
224     }
225 
226     list2->prev->next = list1->next;
227     list1->next->prev = list2->prev;
228     list1->next = list2->next;
229     list2->next->prev = list1;
230 }
231 
232 /*
233  * 功能描述:
234     将链表2中从第一个元素到last_node元素摘出, 加入空链表1的头部
235  */
hi_list_remove_head(hi_list * list1,hi_list * list2,hi_list * last_node)236 static inline hi_void hi_list_remove_head(hi_list *list1, hi_list *list2, hi_list *last_node)
237 {
238     /* 对list1赋值 */
239     list1->next = list2->next;
240     list1->prev = last_node;
241 
242     list2->next = last_node->next;
243     ((hi_list *)(last_node->next))->prev = list2;
244 
245     last_node->next = list1;
246     /* last_node为list2中第一个成员 */
247     if (last_node->prev == list2) {
248         last_node->prev = list1;
249     }
250 }
251 
252 #define hi_list_init_macro(_list_name) hi_list _list_name = { (hi_list *)&(_list_name), (hi_list *)&(_list_name) }
253 
254 /* 获取第一个节点指针 */
255 #define hi_list_first(object) ((object)->next)
256 
257 /* 获取最后一个节点指针 */
258 #define hi_list_last(object) ((object)->prev)
259 
260 /*
261  * 功能描述:
262     获取到一个包含双链表的结构体的指针地址。
263  */
264 #define hi_list_entry(item, type, member) ((type *)((char *)(item)-hi_offset_of_member(type, member)))
265 
266 /*
267  * 功能列表:
268     通过LIST遍历每一个成员节点所在结构体的指针入口地址。
269  */
270 #define hi_list_for_each_entry(item, list, type, member)                                \
271     for ((item) = hi_list_entry((list)->next, type, member); &(item)->member != (list); \
272         (item) = hi_list_entry((item)->member.next, type, member))
273 
274 /*
275  * 功能列表:
276     通过LIST遍历每一个成员节点所在结构体的指针入口地址,保存下一个节点的指针,避免当前节点处理完成后删除的场景。
277  */
278 #define hi_list_for_each_entry_safe(list, item, pnext, type, member) \
279     for ((item) = hi_list_entry((list)->next, type, member),         \
280         (pnext) = hi_list_entry((item)->member.next, type, member);  \
281         &(item)->member != (list); (item) = (pnext), (pnext) = hi_list_entry((item)->member.next, type, member))
282 
283 #define hi_list_for_each_entry_continue_safe(pitem, list, item, pnext, type, member) \
284     for ((item) = hi_list_entry((pitem)->next, type, member),                        \
285         (pnext) = hi_list_entry((item)->member.next, type, member);                  \
286         &((item)->member) != (list); (item) = (pnext), (pnext) = hi_list_entry((pnext)->member.next, type, member))
287 
288 /* 双向链表操作简单实现 */
289 #define hi_list_head(list) hi_list list = { &(list), &(list) }
290 
291 #define hi_list_for_each(item, list) for ((item) = (list)->next; (item) != (list); (item) = (item)->next)
292 
293 #define hi_list_for_each_safe(item, pnext, list) \
294     for ((item) = (list)->next, (pnext) = (item)->next; (item) != (list); (item) = (pnext), (pnext) = (item)->next)
295 
296 HI_END_HEADER
297 #endif /* __HI_STDLIB_H__ */
298