/*
(c) Copyright 2004 convergence GmbH
All rights reserved.
Written by Michael Hunold <hunold@convergence.de> and
Denis Oliver Kropp <dok@directfb.org>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the
Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA.
*/
#ifndef __SOFTMPEG__LIST_H__
#define __SOFTMPEG__LIST_H__
#include "internal.h"
/* Simple doubly linked list implementation
with additional item count and mutex for locking */
struct list_element {
struct list_element *next, *prev;
};
struct list {
struct list_element head;
unsigned int offset;
pthread_mutex_t mutex;
unsigned int items;
};
#define link_to_element(liste, link) \
(void*) (((char*) link) - (liste)->offset)
#define element_to_link(liste, element) \
(struct list_element*) (((char*) element) + (liste)->offset)
static __inline__ void list_init(struct list *l, unsigned int offset)
{
l->head.next = &l->head;
l->head.prev = &l->head;
l->items = 0;
l->offset = offset;
pthread_mutex_init(&l->mutex, NULL);
}
static __inline__ void list_lock(struct list *l)
{
pthread_mutex_lock(&l->mutex);
}
static __inline__ void list_unlock(struct list *l)
{
pthread_mutex_unlock(&l->mutex);
}
static __inline__ void list_add_tail(void *new_element, struct list *l)
{
struct list_element *to_add = element_to_link(l, new_element);
struct list_element *prev = l->head.prev;
struct list_element *next = &l->head;
next->prev = to_add;
to_add->next = next;
to_add->prev = prev;
prev->next = to_add;
l->items++;
}
static __inline__ void element_del(struct list_element *entry)
{
struct list_element *prev = entry->prev;
struct list_element *next = entry->next;
next->prev = prev;
prev->next = next;
}
static __inline__ void *list_del_head(struct list *l)
{
struct list_element *lh = l->head.next;
element_del(lh);
l->items--;
return link_to_element(l, lh);
}
static __inline__ void *list_get_head(struct list *l)
{
struct list_element *lh = l->head.next;
return link_to_element(l, lh);
}
static __inline__ int list_empty(struct list *l)
{
return l->head.next == &l->head;
}
#endif
LinuxTV legacy CVS <linuxtv.org/cvs>