/* * Copyright (C) 2022 Huawei Technologies Co., Ltd. * Licensed under the Mulan PSL v2. * You can use this software according to the terms and conditions of the Mulan PSL v2. * You may obtain a copy of Mulan PSL v2 at: * http://license.coscl.org.cn/MulanPSL2 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR * PURPOSE. * See the Mulan PSL v2 for more details. */ #ifndef TEE_CLIENT_LIST_H #define TEE_CLIENT_LIST_H #include "tee_client_type.h" #define OFFSET_OF(type, member) (unsigned long)(&(((type *)0)->member)) #define CONTAINER_OF(pos, type, member) (type *)(((char *)(pos)) - OFFSET_OF(type, member)) #define LIST_DECLARE(name) \ struct ListNode name = { \ .next = &(name), \ .prev = &(name), \ } static inline void ListInit(struct ListNode *list) { list->next = list; list->prev = list; } #define LIST_HEAD(list) ((list)->next) #define LIST_TAIL(list) ((list)->prev) #define LIST_EMPTY(list) ((list) == (list)->next) static inline void ListInsertHead(struct ListNode *list, struct ListNode *entry) { list->next->prev = entry; entry->next = list->next; entry->prev = list; list->next = entry; } static inline void ListInsertTail(struct ListNode *list, struct ListNode *entry) { entry->next = list; entry->prev = list->prev; list->prev->next = entry; list->prev = entry; } static inline void ListRemoveEntry(struct ListNode *entry) { entry->prev->next = entry->next; entry->next->prev = entry->prev; } static inline struct ListNode *ListRemoveHead(struct ListNode *list) { struct ListNode *entry = NULL; if (!LIST_EMPTY(list)) { entry = list->next; ListRemoveEntry(entry); } return entry; } static inline struct ListNode *ListRemoveTail(struct ListNode *list) { struct ListNode *entry = NULL; if (!LIST_EMPTY(list)) { entry = list->prev; ListRemoveEntry(entry); } return entry; } #define LIST_ENTRY(ptr, type, member) \ ((type *)(((char *)(ptr)) - (unsigned long)(&(((type *)0)->member)))) #define LIST_FOR_EACH(pos, list) \ for ((pos) = (list)->next; (pos) != (list); (pos) = (pos)->next) #define LIST_FOR_EACH_SAFE(pos, n, list) \ for ((pos) = (list)->next, (n) = (pos)->next; (pos) != (list); (pos) = (n), (n) = (pos)->next) #define LIST_FOR_EACH_ENTRY(pos, list, member) \ do { \ for ((pos) = LIST_ENTRY((list)->next, typeof(*(pos)), (member)); &(pos)->(member) != (list); \ (pos) = LIST_ENTRY((pos)->(member).next, typeof(*(pos)), (member))) \ } while (0) #define LIST_FOR_EACH_ENTRY_SAFE(pos, n, list, member) \ do { \ for ((pos) = LIST_ENTRY((list)->next, typeof(*(pos)), (member)), \ (n) = LIST_ENTRY((pos)->(member).next, typeof(*(pos)), (member)); \ &(pos)->(member) != (list); (pos) = (n), (n) = LIST_ENTRY((n)->(member).next, typeof(*(n)), (member))) \ } while (0) #endif