summaryrefslogtreecommitdiff
path: root/src/libstrongswan/utils/linked_list.c
diff options
context:
space:
mode:
authorYves-Alexis Perez <corsac@corsac.net>2012-06-28 21:16:07 +0200
committerYves-Alexis Perez <corsac@corsac.net>2012-06-28 21:16:07 +0200
commitb34738ed08c2227300d554b139e2495ca5da97d6 (patch)
tree62f33b52820f2e49f0e53c0f8c636312037c8054 /src/libstrongswan/utils/linked_list.c
parent0a9d51a49042a68daa15b0c74a2b7f152f52606b (diff)
downloadvyos-strongswan-b34738ed08c2227300d554b139e2495ca5da97d6.tar.gz
vyos-strongswan-b34738ed08c2227300d554b139e2495ca5da97d6.zip
Imported Upstream version 4.6.4
Diffstat (limited to 'src/libstrongswan/utils/linked_list.c')
-rw-r--r--src/libstrongswan/utils/linked_list.c547
1 files changed, 174 insertions, 373 deletions
diff --git a/src/libstrongswan/utils/linked_list.c b/src/libstrongswan/utils/linked_list.c
index 9b37359dc..59d416f2f 100644
--- a/src/libstrongswan/utils/linked_list.c
+++ b/src/libstrongswan/utils/linked_list.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2007-2008 Tobias Brunner
+ * Copyright (C) 2007-2011 Tobias Brunner
* Copyright (C) 2005-2006 Martin Willi
* Copyright (C) 2005 Jan Hutter
* Hochschule fuer Technik Rapperswil
@@ -51,13 +51,11 @@ struct element_t {
*/
element_t *element_create(void *value)
{
- element_t *this = malloc_thing(element_t);
-
- this->previous = NULL;
- this->next = NULL;
- this->value = value;
-
- return (this);
+ element_t *this;
+ INIT(this,
+ .value = value,
+ );
+ return this;
}
@@ -91,34 +89,6 @@ struct private_linked_list_t {
element_t *last;
};
-
-typedef struct private_iterator_t private_iterator_t;
-
-/**
- * Private variables and functions of linked list iterator.
- */
-struct private_iterator_t {
- /**
- * Public part of linked list iterator.
- */
- iterator_t public;
-
- /**
- * Associated linked list.
- */
- private_linked_list_t * list;
-
- /**
- * Current element of the iterator.
- */
- element_t *current;
-
- /**
- * Direction of iterator.
- */
- bool forward;
-};
-
typedef struct private_enumerator_t private_enumerator_t;
/**
@@ -140,241 +110,78 @@ struct private_enumerator_t {
* current item
*/
element_t *current;
+
+ /**
+ * enumerator has enumerated all items
+ */
+ bool finished;
};
-/**
- * Implementation of private_enumerator_t.enumerator.enumerate.
- */
-static bool enumerate(private_enumerator_t *this, void **item)
+METHOD(enumerator_t, enumerate, bool,
+ private_enumerator_t *this, void **item)
{
+ if (this->finished)
+ {
+ return FALSE;
+ }
if (!this->current)
{
- if (!this->list->first)
- {
- return FALSE;
- }
this->current = this->list->first;
}
else
{
- if (!this->current->next)
- {
- return FALSE;
- }
this->current = this->current->next;
}
- *item = this->current->value;
- return TRUE;
-}
-
-/**
- * Implementation of linked_list_t.create_enumerator.
- */
-static enumerator_t* create_enumerator(private_linked_list_t *this)
-{
- private_enumerator_t *enumerator = malloc_thing(private_enumerator_t);
-
- enumerator->enumerator.enumerate = (void*)enumerate;
- enumerator->enumerator.destroy = (void*)free;
- enumerator->list = this;
- enumerator->current = NULL;
-
- return &enumerator->enumerator;
-}
-
-/**
- * Implementation of iterator_t.get_count.
- */
-static int get_list_count(private_iterator_t *this)
-{
- return this->list->count;
-}
-
-/**
- * Implementation of iterator_t.iterate.
- */
-static bool iterate(private_iterator_t *this, void** value)
-{
- if (this->forward)
- {
- this->current = this->current ? this->current->next : this->list->first;
- }
- else
- {
- this->current = this->current ? this->current->previous : this->list->last;
- }
- if (this->current == NULL)
+ if (!this->current)
{
+ this->finished = TRUE;
return FALSE;
}
- *value = this->current->value;
+ *item = this->current->value;
return TRUE;
}
-/**
- * Implementation of iterator_t.reset.
- */
-static void iterator_reset(private_iterator_t *this)
+METHOD(linked_list_t, create_enumerator, enumerator_t*,
+ private_linked_list_t *this)
{
- this->current = NULL;
-}
+ private_enumerator_t *enumerator;
-/**
- * Implementation of iterator_t.remove.
- */
-static status_t iterator_remove(private_iterator_t *this)
-{
- element_t *new_current;
+ INIT(enumerator,
+ .enumerator = {
+ .enumerate = (void*)_enumerate,
+ .destroy = (void*)free,
+ },
+ .list = this,
+ );
- if (this->current == NULL)
- {
- return NOT_FOUND;
- }
-
- if (this->list->count == 0)
- {
- return NOT_FOUND;
- }
- /* find out the new iterator position, depending on iterator direction */
- if (this->forward && this->current->previous != NULL)
- {
- new_current = this->current->previous;
- }
- else if (!this->forward && this->current->next != NULL)
- {
- new_current = this->current->next;
- }
- else
- {
- new_current = NULL;
- }
-
- /* now delete the entry :-) */
- if (this->current->previous == NULL)
- {
- if (this->current->next == NULL)
- {
- this->list->first = NULL;
- this->list->last = NULL;
- }
- else
- {
- this->current->next->previous = NULL;
- this->list->first = this->current->next;
- }
- }
- else if (this->current->next == NULL)
- {
- this->current->previous->next = NULL;
- this->list->last = this->current->previous;
- }
- else
- {
- this->current->previous->next = this->current->next;
- this->current->next->previous = this->current->previous;
- }
-
- this->list->count--;
- free(this->current);
- /* set the new iterator position */
- this->current = new_current;
- return SUCCESS;
-}
-
-/**
- * Implementation of iterator_t.insert_before.
- */
-static void insert_before(private_iterator_t * iterator, void *item)
-{
- if (iterator->current == NULL)
- {
- iterator->list->public.insert_first(&(iterator->list->public), item);
- return;
- }
-
- element_t *element = element_create(item);
- if (iterator->current->previous == NULL)
- {
- iterator->current->previous = element;
- element->next = iterator->current;
- iterator->list->first = element;
- }
- else
- {
- iterator->current->previous->next = element;
- element->previous = iterator->current->previous;
- iterator->current->previous = element;
- element->next = iterator->current;
- }
- iterator->list->count++;
+ return &enumerator->enumerator;
}
-/**
- * Implementation of iterator_t.replace.
- */
-static status_t replace(private_iterator_t *this, void **old_item, void *new_item)
+METHOD(linked_list_t, reset_enumerator, void,
+ private_linked_list_t *this, private_enumerator_t *enumerator)
{
- if (this->current == NULL)
- {
- return NOT_FOUND;
- }
- if (old_item != NULL)
- {
- *old_item = this->current->value;
- }
- this->current->value = new_item;
-
- return SUCCESS;
+ enumerator->current = NULL;
+ enumerator->finished = FALSE;
}
-/**
- * Implementation of iterator_t.insert_after.
- */
-static void insert_after(private_iterator_t *iterator, void *item)
+METHOD(linked_list_t, has_more, bool,
+ private_linked_list_t *this, private_enumerator_t *enumerator)
{
- if (iterator->current == NULL)
- {
- iterator->list->public.insert_first(&(iterator->list->public),item);
- return;
- }
-
- element_t *element = element_create(item);
- if (iterator->current->next == NULL)
- {
- iterator->current->next = element;
- element->previous = iterator->current;
- iterator->list->last = element;
- }
- else
+ if (enumerator->current)
{
- iterator->current->next->previous = element;
- element->next = iterator->current->next;
- iterator->current->next = element;
- element->previous = iterator->current;
+ return enumerator->current->next != NULL;
}
- iterator->list->count++;
+ return !enumerator->finished && this->first != NULL;
}
-/**
- * Implementation of iterator_t.destroy.
- */
-static void iterator_destroy(private_iterator_t *this)
-{
- free(this);
-}
-
-/**
- * Implementation of linked_list_t.get_count.
- */
-static int get_count(private_linked_list_t *this)
+METHOD(linked_list_t, get_count, int,
+ private_linked_list_t *this)
{
return this->count;
}
-/**
- * Implementation of linked_list_t.insert_first.
- */
-static void insert_first(private_linked_list_t *this, void *item)
+METHOD(linked_list_t, insert_first, void,
+ private_linked_list_t *this, void *item)
{
element_t *element;
@@ -384,15 +191,11 @@ static void insert_first(private_linked_list_t *this, void *item)
/* first entry in list */
this->first = element;
this->last = element;
- element->previous = NULL;
- element->next = NULL;
}
else
{
- element_t *old_first_element = this->first;
- element->next = old_first_element;
- element->previous = NULL;
- old_first_element->previous = element;
+ element->next = this->first;
+ this->first->previous = element;
this->first = element;
}
this->count++;
@@ -401,7 +204,8 @@ static void insert_first(private_linked_list_t *this, void *item)
/**
* unlink an element form the list, returns following element
*/
-static element_t* remove_element(private_linked_list_t *this, element_t *element)
+static element_t* remove_element(private_linked_list_t *this,
+ element_t *element)
{
element_t *next, *previous;
@@ -432,10 +236,8 @@ static element_t* remove_element(private_linked_list_t *this, element_t *element
return next;
}
-/**
- * Implementation of linked_list_t.get_first.
- */
-static status_t get_first(private_linked_list_t *this, void **item)
+METHOD(linked_list_t, get_first, status_t,
+ private_linked_list_t *this, void **item)
{
if (this->count == 0)
{
@@ -445,10 +247,8 @@ static status_t get_first(private_linked_list_t *this, void **item)
return SUCCESS;
}
-/**
- * Implementation of linked_list_t.remove_first.
- */
-static status_t remove_first(private_linked_list_t *this, void **item)
+METHOD(linked_list_t, remove_first, status_t,
+ private_linked_list_t *this, void **item)
{
if (get_first(this, item) == SUCCESS)
{
@@ -458,36 +258,79 @@ static status_t remove_first(private_linked_list_t *this, void **item)
return NOT_FOUND;
}
-/**
- * Implementation of linked_list_t.insert_last.
- */
-static void insert_last(private_linked_list_t *this, void *item)
+METHOD(linked_list_t, insert_last, void,
+ private_linked_list_t *this, void *item)
{
- element_t *element = element_create(item);
+ element_t *element;
+ element = element_create(item);
if (this->count == 0)
{
/* first entry in list */
this->first = element;
this->last = element;
- element->previous = NULL;
- element->next = NULL;
}
else
{
- element_t *old_last_element = this->last;
- element->previous = old_last_element;
- element->next = NULL;
- old_last_element->next = element;
+ element->previous = this->last;
+ this->last->next = element;
this->last = element;
}
this->count++;
}
-/**
- * Implementation of linked_list_t.get_last.
- */
-static status_t get_last(private_linked_list_t *this, void **item)
+METHOD(linked_list_t, insert_before, void,
+ private_linked_list_t *this, private_enumerator_t *enumerator,
+ void *item)
+{
+ element_t *current, *element;
+
+ current = enumerator->current;
+ if (!current)
+ {
+ if (enumerator->finished)
+ {
+ this->public.insert_last(&this->public, item);
+ }
+ else
+ {
+ this->public.insert_first(&this->public, item);
+ }
+ return;
+ }
+ element = element_create(item);
+ if (current->previous)
+ {
+ current->previous->next = element;
+ element->previous = current->previous;
+ current->previous = element;
+ element->next = current;
+ }
+ else
+ {
+ current->previous = element;
+ element->next = current;
+ this->first = element;
+ }
+ this->count++;
+}
+
+METHOD(linked_list_t, replace, void*,
+ private_linked_list_t *this, private_enumerator_t *enumerator,
+ void *item)
+{
+ void *old = NULL;
+
+ if (enumerator->current)
+ {
+ old = enumerator->current->value;
+ enumerator->current->value = item;
+ }
+ return old;
+}
+
+METHOD(linked_list_t, get_last, status_t,
+ private_linked_list_t *this, void **item)
{
if (this->count == 0)
{
@@ -497,10 +340,8 @@ static status_t get_last(private_linked_list_t *this, void **item)
return SUCCESS;
}
-/**
- * Implementation of linked_list_t.remove_last.
- */
-static status_t remove_last(private_linked_list_t *this, void **item)
+METHOD(linked_list_t, remove_last, status_t,
+ private_linked_list_t *this, void **item)
{
if (get_last(this, item) == SUCCESS)
{
@@ -510,11 +351,8 @@ static status_t remove_last(private_linked_list_t *this, void **item)
return NOT_FOUND;
}
-/**
- * Implementation of linked_list_t.remove.
- */
-static int remove_(private_linked_list_t *this, void *item,
- bool (*compare)(void *,void*))
+METHOD(linked_list_t, remove_, int,
+ private_linked_list_t *this, void *item, bool (*compare)(void*,void*))
{
element_t *current = this->first;
int removed = 0;
@@ -535,10 +373,8 @@ static int remove_(private_linked_list_t *this, void *item,
return removed;
}
-/**
- * Implementation of linked_list_t.remove_at.
- */
-static void remove_at(private_linked_list_t *this, private_enumerator_t *enumerator)
+METHOD(linked_list_t, remove_at, void,
+ private_linked_list_t *this, private_enumerator_t *enumerator)
{
element_t *current;
@@ -550,11 +386,9 @@ static void remove_at(private_linked_list_t *this, private_enumerator_t *enumera
}
}
-/**
- * Implementation of linked_list_t.find_first.
- */
-static status_t find_first(private_linked_list_t *this, linked_list_match_t match,
- void **item, void *d1, void *d2, void *d3, void *d4, void *d5)
+METHOD(linked_list_t, find_first, status_t,
+ private_linked_list_t *this, linked_list_match_t match,
+ void **item, void *d1, void *d2, void *d3, void *d4, void *d5)
{
element_t *current = this->first;
@@ -574,11 +408,9 @@ static status_t find_first(private_linked_list_t *this, linked_list_match_t matc
return NOT_FOUND;
}
-/**
- * Implementation of linked_list_t.find_last.
- */
-static status_t find_last(private_linked_list_t *this, linked_list_match_t match,
- void **item, void *d1, void *d2, void *d3, void *d4, void *d5)
+METHOD(linked_list_t, find_last, status_t,
+ private_linked_list_t *this, linked_list_match_t match,
+ void **item, void *d1, void *d2, void *d3, void *d4, void *d5)
{
element_t *current = this->last;
@@ -598,27 +430,24 @@ static status_t find_last(private_linked_list_t *this, linked_list_match_t match
return NOT_FOUND;
}
-/**
- * Implementation of linked_list_t.invoke_offset.
- */
-static void invoke_offset(private_linked_list_t *this, size_t offset,
- void *d1, void *d2, void *d3, void *d4, void *d5)
+METHOD(linked_list_t, invoke_offset, void,
+ private_linked_list_t *this, size_t offset,
+ void *d1, void *d2, void *d3, void *d4, void *d5)
{
element_t *current = this->first;
+ linked_list_invoke_t *method;
while (current)
{
- linked_list_invoke_t *method = current->value + offset;
+ method = current->value + offset;
(*method)(current->value, d1, d2, d3, d4, d5);
current = current->next;
}
}
-/**
- * Implementation of linked_list_t.invoke_function.
- */
-static void invoke_function(private_linked_list_t *this, linked_list_invoke_t fn,
- void *d1, void *d2, void *d3, void *d4, void *d5)
+METHOD(linked_list_t, invoke_function, void,
+ private_linked_list_t *this, linked_list_invoke_t fn,
+ void *d1, void *d2, void *d3, void *d4, void *d5)
{
element_t *current = this->first;
@@ -629,14 +458,13 @@ static void invoke_function(private_linked_list_t *this, linked_list_invoke_t fn
}
}
-/**
- * Implementation of linked_list_t.clone_offset
- */
-static linked_list_t *clone_offset(private_linked_list_t *this, size_t offset)
+METHOD(linked_list_t, clone_offset, linked_list_t*,
+ private_linked_list_t *this, size_t offset)
{
- linked_list_t *clone = linked_list_create();
element_t *current = this->first;
+ linked_list_t *clone;
+ clone = linked_list_create();
while (current)
{
void* (**method)(void*) = current->value + offset;
@@ -647,29 +475,26 @@ static linked_list_t *clone_offset(private_linked_list_t *this, size_t offset)
return clone;
}
-/**
- * Implementation of linked_list_t.clone_function
- */
-static linked_list_t *clone_function(private_linked_list_t *this, void* (*fn)(void*))
+METHOD(linked_list_t, clone_function, linked_list_t*,
+ private_linked_list_t *this, void* (*fn)(void*))
{
- linked_list_t *clone = linked_list_create();
element_t *current = this->first;
+ linked_list_t *clone;
+ clone = linked_list_create();
while (current)
{
clone->insert_last(clone, fn(current->value));
current = current->next;
}
-
return clone;
}
-/**
- * Implementation of linked_list_t.destroy.
- */
-static void destroy(private_linked_list_t *this)
+METHOD(linked_list_t, destroy, void,
+ private_linked_list_t *this)
{
void *value;
+
/* Remove all list items before destroying list */
while (remove_first(this, &value) == SUCCESS)
{
@@ -679,10 +504,8 @@ static void destroy(private_linked_list_t *this)
free(this);
}
-/**
- * Implementation of linked_list_t.destroy_offset.
- */
-static void destroy_offset(private_linked_list_t *this, size_t offset)
+METHOD(linked_list_t, destroy_offset, void,
+ private_linked_list_t *this, size_t offset)
{
element_t *current = this->first, *next;
@@ -697,10 +520,8 @@ static void destroy_offset(private_linked_list_t *this, size_t offset)
free(this);
}
-/**
- * Implementation of linked_list_t.destroy_function.
- */
-static void destroy_function(private_linked_list_t *this, void (*fn)(void*))
+METHOD(linked_list_t, destroy_function, void,
+ private_linked_list_t *this, void (*fn)(void*))
{
element_t *current = this->first, *next;
@@ -714,60 +535,40 @@ static void destroy_function(private_linked_list_t *this, void (*fn)(void*))
free(this);
}
-/**
- * Implementation of linked_list_t.create_iterator.
- */
-static iterator_t *create_iterator(private_linked_list_t *linked_list, bool forward)
-{
- private_iterator_t *this = malloc_thing(private_iterator_t);
-
- this->public.get_count = (int (*) (iterator_t*)) get_list_count;
- this->public.iterate = (bool (*) (iterator_t*, void **value)) iterate;
- this->public.insert_before = (void (*) (iterator_t*, void *item)) insert_before;
- this->public.insert_after = (void (*) (iterator_t*, void *item)) insert_after;
- this->public.replace = (status_t (*) (iterator_t*, void **, void *)) replace;
- this->public.remove = (status_t (*) (iterator_t*)) iterator_remove;
- this->public.reset = (void (*) (iterator_t*)) iterator_reset;
- this->public.destroy = (void (*) (iterator_t*)) iterator_destroy;
-
- this->forward = forward;
- this->current = NULL;
- this->list = linked_list;
-
- return &this->public;
-}
-
/*
* Described in header.
*/
linked_list_t *linked_list_create()
{
- private_linked_list_t *this = malloc_thing(private_linked_list_t);
-
- this->public.get_count = (int (*) (linked_list_t *)) get_count;
- this->public.create_iterator = (iterator_t * (*) (linked_list_t *,bool))create_iterator;
- this->public.create_enumerator = (enumerator_t*(*)(linked_list_t*))create_enumerator;
- this->public.get_first = (status_t (*) (linked_list_t *, void **item))get_first;
- this->public.get_last = (status_t (*) (linked_list_t *, void **item))get_last;
- this->public.find_first = (status_t (*) (linked_list_t *, linked_list_match_t,void**,...))find_first;
- this->public.find_last = (status_t (*) (linked_list_t *, linked_list_match_t,void**,...))find_last;
- this->public.insert_first = (void (*) (linked_list_t *, void *item))insert_first;
- this->public.insert_last = (void (*) (linked_list_t *, void *item))insert_last;
- this->public.remove_first = (status_t (*) (linked_list_t *, void **item))remove_first;
- this->public.remove_last = (status_t (*) (linked_list_t *, void **item))remove_last;
- this->public.remove = (int(*)(linked_list_t*, void *item, bool (*compare)(void *,void*)))remove_;
- this->public.remove_at = (void(*)(linked_list_t*, enumerator_t *enumerator))remove_at;
- this->public.invoke_offset = (void (*)(linked_list_t*,size_t,...))invoke_offset;
- this->public.invoke_function = (void (*)(linked_list_t*,linked_list_invoke_t,...))invoke_function;
- this->public.clone_offset = (linked_list_t * (*)(linked_list_t*,size_t))clone_offset;
- this->public.clone_function = (linked_list_t * (*)(linked_list_t*,void*(*)(void*)))clone_function;
- this->public.destroy = (void (*) (linked_list_t *))destroy;
- this->public.destroy_offset = (void (*) (linked_list_t *,size_t))destroy_offset;
- this->public.destroy_function = (void (*)(linked_list_t*,void(*)(void*)))destroy_function;
-
- this->count = 0;
- this->first = NULL;
- this->last = NULL;
+ private_linked_list_t *this;
+
+ INIT(this,
+ .public = {
+ .get_count = _get_count,
+ .create_enumerator = _create_enumerator,
+ .reset_enumerator = (void*)_reset_enumerator,
+ .has_more = (void*)_has_more,
+ .get_first = _get_first,
+ .get_last = _get_last,
+ .find_first = (void*)_find_first,
+ .find_last = (void*)_find_last,
+ .insert_first = _insert_first,
+ .insert_last = _insert_last,
+ .insert_before = (void*)_insert_before,
+ .replace = (void*)_replace,
+ .remove_first = _remove_first,
+ .remove_last = _remove_last,
+ .remove = _remove_,
+ .remove_at = (void*)_remove_at,
+ .invoke_offset = (void*)_invoke_offset,
+ .invoke_function = (void*)_invoke_function,
+ .clone_offset = _clone_offset,
+ .clone_function = _clone_function,
+ .destroy = _destroy,
+ .destroy_offset = _destroy_offset,
+ .destroy_function = _destroy_function,
+ },
+ );
return &this->public;
}