summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarcel Hollerbach <marcel-hollerbach@t-online.de>2016-12-08 19:53:22 +0100
committerMarcel Hollerbach <marcel-hollerbach@t-online.de>2016-12-09 10:16:08 +0100
commit712ec600121f23a413ce8e328f3b0d21e0b35e6a (patch)
tree77872b3d81d9c4c8078c284013f93532cdf0049d
parent8784ba97ad2adea5b3709e35c90da56ad9a6d702 (diff)
downloadefl-712ec600121f23a413ce8e328f3b0d21e0b35e6a.tar.gz
eina: add free cb to eina_iterator_filter_new
if you allocate memory for the data param data you can free it in this callback.
-rw-r--r--src/lib/eina/eina_iterator.c6
-rw-r--r--src/lib/eina/eina_iterator.h3
-rw-r--r--src/tests/eina/eina_test_iterator.c44
3 files changed, 50 insertions, 3 deletions
diff --git a/src/lib/eina/eina_iterator.c b/src/lib/eina/eina_iterator.c
index ba64bf2437..4a4e281079 100644
--- a/src/lib/eina/eina_iterator.c
+++ b/src/lib/eina/eina_iterator.c
@@ -235,6 +235,7 @@ typedef struct {
void *data;
Eina_Iterator *original;
Eina_Each_Cb cb;
+ Eina_Free_Cb free;
} Eina_Iterator_Filter;
static Eina_Bool
@@ -259,12 +260,14 @@ eina_iterator_filter_get_container(Eina_Iterator_Filter *it)
static void
eina_iterator_filter_free(Eina_Iterator_Filter *it)
{
+ if (it->free)
+ it->free(it->data);
eina_iterator_free(it->original);
free(it);
}
EAPI Eina_Iterator*
-eina_iterator_filter_new(Eina_Iterator *iterator, Eina_Each_Cb filter, void *data)
+eina_iterator_filter_new(Eina_Iterator *iterator, Eina_Each_Cb filter, Eina_Free_Cb free_cb, void *data)
{
Eina_Iterator_Filter *it;
@@ -276,6 +279,7 @@ eina_iterator_filter_new(Eina_Iterator *iterator, Eina_Each_Cb filter, void *dat
it->original = iterator;
it->data = data;
it->cb = filter;
+ it->free = free_cb;
EINA_MAGIC_SET(&it->iterator, EINA_MAGIC_ITERATOR);
diff --git a/src/lib/eina/eina_iterator.h b/src/lib/eina/eina_iterator.h
index 304af32d5e..fadf1df710 100644
--- a/src/lib/eina/eina_iterator.h
+++ b/src/lib/eina/eina_iterator.h
@@ -305,6 +305,7 @@ EAPI Eina_Iterator* eina_carray_iterator_new(void** array) EINA_ARG_NONNULL(1) E
*
* @param original the iterator the use as original set
* @param filter if the callback returns true the element from the original set is taken into the the new set.
+ * @param free_cb when the iterator is gone this callback will be called with data as argument
* @param data the data which is passed to the filter callback
*
* The iterator is filtered while it is beeing iterated.
@@ -312,7 +313,7 @@ EAPI Eina_Iterator* eina_carray_iterator_new(void** array) EINA_ARG_NONNULL(1) E
*
* @since 1.19
*/
-EAPI Eina_Iterator* eina_iterator_filter_new(Eina_Iterator *original, Eina_Each_Cb filter, void *data) EINA_ARG_NONNULL(1) EINA_WARN_UNUSED_RESULT;
+EAPI Eina_Iterator* eina_iterator_filter_new(Eina_Iterator *original, Eina_Each_Cb filter, Eina_Free_Cb free_cb, void *data) EINA_ARG_NONNULL(1) EINA_WARN_UNUSED_RESULT;
/**
* @def EINA_ITERATOR_FOREACH
diff --git a/src/tests/eina/eina_test_iterator.c b/src/tests/eina/eina_test_iterator.c
index ea695efc36..2066269dcc 100644
--- a/src/tests/eina/eina_test_iterator.c
+++ b/src/tests/eina/eina_test_iterator.c
@@ -60,7 +60,7 @@ START_TEST(eina_iterator_filter_simple)
}
it = eina_array_iterator_new(ea);
- filtered = eina_iterator_filter_new(it, _filter, (void*)1);
+ filtered = eina_iterator_filter_new(it, _filter, NULL, (void*)1);
for(int i = 1; i <= 10; i+=2)
{
struct Number *numb;
@@ -89,6 +89,47 @@ START_TEST(eina_iterator_filter_simple)
}
END_TEST
+struct Free_test {
+ Eina_Bool got_freed;
+};
+
+static Eina_Bool
+_filter_free(const void *it EINA_UNUSED, void *data EINA_UNUSED, void *fdata EINA_UNUSED)
+{
+ return EINA_TRUE;
+}
+
+static void
+_free(void *data)
+{
+ struct Free_test *test = data;
+ test->got_freed = EINA_TRUE;
+}
+
+START_TEST(eina_iterator_filter_free)
+{
+ Eina_Iterator *it, *filtered;
+ Eina_Array *ea;
+ struct Free_test *data;
+ eina_init();
+
+ data = calloc(1, sizeof(struct Free_test));
+ ea = eina_array_new(11);
+ fail_if(!ea);
+
+ it = eina_array_iterator_new(ea);
+ filtered = eina_iterator_filter_new(it, _filter_free, _free, data);
+ eina_iterator_free(filtered);
+
+ eina_array_free(ea);
+
+ ck_assert_int_ne(data->got_freed, 0);
+
+ free(data);
+
+ eina_shutdown();
+}
+END_TEST
static Eina_Bool
eina_iterator_array_check(EINA_UNUSED const Eina_Array *array,
int *data, int *fdata)
@@ -593,4 +634,5 @@ eina_test_iterator(TCase *tc)
tcase_add_test(tc, eina_reverse_iterator_list_simple);
tcase_add_test(tc, eina_iterator_rbtree_simple);
tcase_add_test(tc, eina_iterator_filter_simple);
+ tcase_add_test(tc, eina_iterator_filter_free);
}