a23fd118e437af0a7877dd313db8fdaa3537c675yl/*
a23fd118e437af0a7877dd313db8fdaa3537c675yl * CDDL HEADER START
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * The contents of this file are subject to the terms of the
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Common Development and Distribution License (the "License").
a23fd118e437af0a7877dd313db8fdaa3537c675yl * You may not use this file except in compliance with the License.
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
a23fd118e437af0a7877dd313db8fdaa3537c675yl * or http://www.opensolaris.org/os/licensing.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * See the License for the specific language governing permissions
a23fd118e437af0a7877dd313db8fdaa3537c675yl * and limitations under the License.
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * When distributing Covered Code, include this CDDL HEADER in each
a23fd118e437af0a7877dd313db8fdaa3537c675yl * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * If applicable, add the following below this CDDL HEADER, with the
a23fd118e437af0a7877dd313db8fdaa3537c675yl * fields enclosed by brackets "[]" replaced with your own identifying
a23fd118e437af0a7877dd313db8fdaa3537c675yl * information: Portions Copyright [yyyy] [name of copyright owner]
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * CDDL HEADER END
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * Copyright (c) 2002-2006 Neterion, Inc.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#ifndef XGE_LIST_H
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define XGE_LIST_H
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#include "xge-debug.h"
a23fd118e437af0a7877dd313db8fdaa3537c675yl
8347601bcb0a439f6e50fc36b4039a73d08700e1yl__EXTERN_BEGIN_DECLS
8347601bcb0a439f6e50fc36b4039a73d08700e1yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * struct xge_list_t - List item.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @prev: Previous list item.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @next: Next list item.
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Item of a bi-directional linked list.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675yltypedef struct xge_list_t {
a23fd118e437af0a7877dd313db8fdaa3537c675yl struct xge_list_t* prev;
a23fd118e437af0a7877dd313db8fdaa3537c675yl struct xge_list_t* next;
a23fd118e437af0a7877dd313db8fdaa3537c675yl} xge_list_t;
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_list_init - Initialize linked list.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * header: first element of the list (head)
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Initialize linked list.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * See also: xge_list_t{}.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675ylstatic inline void xge_list_init (xge_list_t *header)
a23fd118e437af0a7877dd313db8fdaa3537c675yl{
a23fd118e437af0a7877dd313db8fdaa3537c675yl header->next = header;
a23fd118e437af0a7877dd313db8fdaa3537c675yl header->prev = header;
a23fd118e437af0a7877dd313db8fdaa3537c675yl}
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_list_is_empty - Is the list empty?
a23fd118e437af0a7877dd313db8fdaa3537c675yl * header: first element of the list (head)
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Determine whether the bi-directional list is empty. Return '1' in
a23fd118e437af0a7877dd313db8fdaa3537c675yl * case of 'empty'.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * See also: xge_list_t{}.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675ylstatic inline int xge_list_is_empty(xge_list_t *header)
a23fd118e437af0a7877dd313db8fdaa3537c675yl{
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(header != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl return header->next == header;
a23fd118e437af0a7877dd313db8fdaa3537c675yl}
a23fd118e437af0a7877dd313db8fdaa3537c675yl
8347601bcb0a439f6e50fc36b4039a73d08700e1yl/**
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * xge_list_first_get - Return the first item from the linked list.
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * header: first element of the list (head)
8347601bcb0a439f6e50fc36b4039a73d08700e1yl *
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * Returns the next item from the header.
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * Returns NULL if the next item is header itself
8347601bcb0a439f6e50fc36b4039a73d08700e1yl * See also: xge_list_remove(), xge_list_insert(), xge_list_t{}.
8347601bcb0a439f6e50fc36b4039a73d08700e1yl */
8347601bcb0a439f6e50fc36b4039a73d08700e1ylstatic inline xge_list_t *xge_list_first_get(xge_list_t *header)
8347601bcb0a439f6e50fc36b4039a73d08700e1yl{
8347601bcb0a439f6e50fc36b4039a73d08700e1yl xge_assert(header != NULL);
8347601bcb0a439f6e50fc36b4039a73d08700e1yl xge_assert(header->next != NULL);
8347601bcb0a439f6e50fc36b4039a73d08700e1yl xge_assert(header->prev != NULL);
8347601bcb0a439f6e50fc36b4039a73d08700e1yl
8347601bcb0a439f6e50fc36b4039a73d08700e1yl if(header->next == header)
8347601bcb0a439f6e50fc36b4039a73d08700e1yl return NULL;
8347601bcb0a439f6e50fc36b4039a73d08700e1yl else
8347601bcb0a439f6e50fc36b4039a73d08700e1yl return header->next;
8347601bcb0a439f6e50fc36b4039a73d08700e1yl}
8347601bcb0a439f6e50fc36b4039a73d08700e1yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_list_remove - Remove the specified item from the linked list.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * item: element of the list
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Remove item from a list.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * See also: xge_list_insert(), xge_list_t{}.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675ylstatic inline void xge_list_remove(xge_list_t *item)
a23fd118e437af0a7877dd313db8fdaa3537c675yl{
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(item != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(item->next != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(item->prev != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl item->next->prev = item->prev;
a23fd118e437af0a7877dd313db8fdaa3537c675yl item->prev->next = item->next;
a23fd118e437af0a7877dd313db8fdaa3537c675yl#ifdef XGE_DEBUG_ASSERT
a23fd118e437af0a7877dd313db8fdaa3537c675yl item->next = item->prev = NULL;
a23fd118e437af0a7877dd313db8fdaa3537c675yl#endif
a23fd118e437af0a7877dd313db8fdaa3537c675yl}
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_list_insert - Insert a new item after the specified item.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * new_item: new element of the list
a23fd118e437af0a7877dd313db8fdaa3537c675yl * prev_item: element of the list after which the new element is
a23fd118e437af0a7877dd313db8fdaa3537c675yl * inserted
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Insert new item (new_item) after given item (prev_item).
a23fd118e437af0a7877dd313db8fdaa3537c675yl * See also: xge_list_remove(), xge_list_insert_before(), xge_list_t{}.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675ylstatic inline void xge_list_insert (xge_list_t *new_item,
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_list_t *prev_item)
a23fd118e437af0a7877dd313db8fdaa3537c675yl{
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(new_item != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(prev_item != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(prev_item->next != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl new_item->next = prev_item->next;
a23fd118e437af0a7877dd313db8fdaa3537c675yl new_item->prev = prev_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl prev_item->next->prev = new_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl prev_item->next = new_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl}
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_list_insert_before - Insert a new item before the specified item.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * new_item: new element of the list
a23fd118e437af0a7877dd313db8fdaa3537c675yl * next_item: element of the list after which the new element is inserted
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Insert new item (new_item) before given item (next_item).
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675ylstatic inline void xge_list_insert_before (xge_list_t *new_item,
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_list_t *next_item)
a23fd118e437af0a7877dd313db8fdaa3537c675yl{
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(new_item != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(next_item != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl xge_assert(next_item->next != NULL);
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl new_item->next = next_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl new_item->prev = next_item->prev;
a23fd118e437af0a7877dd313db8fdaa3537c675yl next_item->prev->next = new_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl next_item->prev = new_item;
a23fd118e437af0a7877dd313db8fdaa3537c675yl}
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define xge_list_for_each(_p, _h) \
a23fd118e437af0a7877dd313db8fdaa3537c675yl for (_p = (_h)->next, xge_os_prefetch(_p->next); _p != (_h); \
a23fd118e437af0a7877dd313db8fdaa3537c675yl _p = _p->next, xge_os_prefetch(_p->next))
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define xge_list_for_each_safe(_p, _n, _h) \
a23fd118e437af0a7877dd313db8fdaa3537c675yl for (_p = (_h)->next, _n = _p->next; _p != (_h); \
a23fd118e437af0a7877dd313db8fdaa3537c675yl _p = _n, _n = _p->next)
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#ifdef __GNUC__
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_container_of - Given a member, return the containing structure.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @ptr: the pointer to the member.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @type: the type of the container struct this is embedded in.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @member: the name of the member within the struct.
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Cast a member of a structure out to the containing structure.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define xge_container_of(ptr, type, member) ({ \
7eced415e5dd557aef2d78483b5a7785f0e13670xw __typeof( ((type *)0)->member ) *__mptr = (ptr); \
a23fd118e437af0a7877dd313db8fdaa3537c675yl (type *)(void *)( (char *)__mptr - ((size_t) &((type *)0)->member) );})
a23fd118e437af0a7877dd313db8fdaa3537c675yl#else
a23fd118e437af0a7877dd313db8fdaa3537c675yl/* type unsafe version */
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define xge_container_of(ptr, type, member) \
a23fd118e437af0a7877dd313db8fdaa3537c675yl ((type*)(void*)((char*)(ptr) - ((size_t) &((type *)0)->member)))
a23fd118e437af0a7877dd313db8fdaa3537c675yl#endif
a23fd118e437af0a7877dd313db8fdaa3537c675yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl/**
a23fd118e437af0a7877dd313db8fdaa3537c675yl * xge_offsetof - Offset of the member in the containing structure.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @t: struct name.
a23fd118e437af0a7877dd313db8fdaa3537c675yl * @m: the name of the member within the struct.
a23fd118e437af0a7877dd313db8fdaa3537c675yl *
a23fd118e437af0a7877dd313db8fdaa3537c675yl * Return the offset of the member @m in the structure @t.
a23fd118e437af0a7877dd313db8fdaa3537c675yl */
a23fd118e437af0a7877dd313db8fdaa3537c675yl#define xge_offsetof(t, m) ((size_t) (&((t *)0)->m))
a23fd118e437af0a7877dd313db8fdaa3537c675yl
8347601bcb0a439f6e50fc36b4039a73d08700e1yl__EXTERN_END_DECLS
8347601bcb0a439f6e50fc36b4039a73d08700e1yl
a23fd118e437af0a7877dd313db8fdaa3537c675yl#endif /* XGE_LIST_H */