|
@@ -0,0 +1,108 @@
|
|
|
+/*
|
|
|
+ * Copyright Institute of Communication and Computer Systems (ICCS)
|
|
|
+ *
|
|
|
+ * Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
+ * you may not use this file except in compliance with the License.
|
|
|
+ * You may obtain a copy of the License at
|
|
|
+ *
|
|
|
+ * http://www.apache.org/licenses/LICENSE-2.0
|
|
|
+ *
|
|
|
+ * Unless required by applicable law or agreed to in writing, software
|
|
|
+ * distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
+ * See the License for the specific language governing permissions and
|
|
|
+ * limitations under the License.
|
|
|
+ *
|
|
|
+ */
|
|
|
+
|
|
|
+/**
|
|
|
+ * @file lists.h
|
|
|
+ * @author Ioannis Koutras (joko@microlab.ntua.gr)
|
|
|
+ * @date October 2012
|
|
|
+ * @brief Macros for singly-linked lists
|
|
|
+ *
|
|
|
+ * These macros were copied from /usr/include/sys/queue.h
|
|
|
+ *
|
|
|
+ */
|
|
|
+
|
|
|
+#ifndef _DMMLIB_LISTS_H_
|
|
|
+#define _DMMLIB_LISTS_H_
|
|
|
+
|
|
|
+/*
|
|
|
+ * Singly-linked List definitions.
|
|
|
+ */
|
|
|
+
|
|
|
+/** The head of a singly-linked list */
|
|
|
+#define SLIST_HEAD(name, type) \
|
|
|
+struct name { \
|
|
|
+ struct type *slh_first; /* first element */ \
|
|
|
+}
|
|
|
+
|
|
|
+/** Initial value of the head of a singly-linked list */
|
|
|
+#define SLIST_HEAD_INITIALIZER(head) \
|
|
|
+ { NULL }
|
|
|
+
|
|
|
+/** Entry of a singly linked list */
|
|
|
+#define SLIST_ENTRY(type) \
|
|
|
+struct { \
|
|
|
+ struct type *sle_next; /* next element */ \
|
|
|
+}
|
|
|
+
|
|
|
+/*
|
|
|
+ * Singly-linked List functions.
|
|
|
+ */
|
|
|
+
|
|
|
+/** Initializes the head of a singly-linked list */
|
|
|
+#define SLIST_INIT(head) do { \
|
|
|
+ (head)->slh_first = NULL; \
|
|
|
+} while (/*CONSTCOND*/0)
|
|
|
+
|
|
|
+/** Inserts an element after a specific one in a singly-linked list */
|
|
|
+#define SLIST_INSERT_AFTER(slistelm, elm, field) do { \
|
|
|
+ (elm)->field.sle_next = (slistelm)->field.sle_next; \
|
|
|
+ (slistelm)->field.sle_next = (elm); \
|
|
|
+} while (/*CONSTCOND*/0)
|
|
|
+
|
|
|
+/** Inserts an element as the head of a singly-linked list */
|
|
|
+#define SLIST_INSERT_HEAD(head, elm, field) do { \
|
|
|
+ (elm)->field.sle_next = (head)->slh_first; \
|
|
|
+ (head)->slh_first = (elm); \
|
|
|
+} while (/*CONSTCOND*/0)
|
|
|
+
|
|
|
+/** Removes the head element of a singly-linked list */
|
|
|
+#define SLIST_REMOVE_HEAD(head, field) do { \
|
|
|
+ (head)->slh_first = (head)->slh_first->field.sle_next; \
|
|
|
+} while (/*CONSTCOND*/0)
|
|
|
+
|
|
|
+/** Removes an element from a singly-linked list */
|
|
|
+#define SLIST_REMOVE(head, elm, type, field) do { \
|
|
|
+ if ((head)->slh_first == (elm)) { \
|
|
|
+ SLIST_REMOVE_HEAD((head), field); \
|
|
|
+ } \
|
|
|
+ else { \
|
|
|
+ struct type *curelm = (head)->slh_first; \
|
|
|
+ while(curelm->field.sle_next != (elm)) \
|
|
|
+ curelm = curelm->field.sle_next; \
|
|
|
+ curelm->field.sle_next = \
|
|
|
+ curelm->field.sle_next->field.sle_next; \
|
|
|
+ } \
|
|
|
+} while (/*CONSTCOND*/0)
|
|
|
+
|
|
|
+/** Iterates through a singly-linked list */
|
|
|
+#define SLIST_FOREACH(var, head, field) \
|
|
|
+ for((var) = (head)->slh_first; (var); (var) = (var)->field.sle_next)
|
|
|
+
|
|
|
+/*
|
|
|
+ * Singly-linked List access methods.
|
|
|
+ */
|
|
|
+
|
|
|
+/** Empties a singly-linked list */
|
|
|
+#define SLIST_EMPTY(head) ((head)->slh_first == NULL)
|
|
|
+
|
|
|
+/** Gets the head of a singly-linked list */
|
|
|
+#define SLIST_FIRST(head) ((head)->slh_first)
|
|
|
+
|
|
|
+/** Gets the next element of a specific element from a singly-linked list */
|
|
|
+#define SLIST_NEXT(elm, field) ((elm)->field.sle_next)
|
|
|
+
|
|
|
+#endif /* _DMMLIB_LISTS_H_ */
|