From 46843551c0af0b58c67cb2f998ece53a32437748 Mon Sep 17 00:00:00 2001 From: Lauro Moura Date: Wed, 8 Jun 2016 19:33:29 -0300 Subject: [PATCH] eina: Remove value type promises All values in promises are now considered as by-pointer. --- src/benchmarks/eina/eina_bench_promise.c | 124 +---- src/lib/ecore/ecore_thread_promise.c | 22 - src/lib/eina/eina_promise.c | 290 +++-------- src/lib/eina/eina_promise.h | 89 +--- src/lib/eio/eio_job.c | 30 +- src/lib/eio/eio_model.c | 14 +- src/lib/eldbus/eldbus_model_arguments.c | 18 +- src/lib/eldbus/eldbus_model_connection.c | 15 +- src/lib/eldbus/eldbus_model_object.c | 15 +- src/lib/eldbus/eldbus_model_proxy.c | 23 +- src/tests/ecore/ecore_test_job.c | 3 +- src/tests/ecore/ecore_test_promise.c | 8 +- src/tests/eina/eina_suite.c | 104 ++-- src/tests/eina/eina_test_promise.c | 602 ++++++++--------------- 14 files changed, 400 insertions(+), 957 deletions(-) diff --git a/src/benchmarks/eina/eina_bench_promise.c b/src/benchmarks/eina/eina_bench_promise.c index 90a39dfbb8..6baabac9a6 100644 --- a/src/benchmarks/eina/eina_bench_promise.c +++ b/src/benchmarks/eina/eina_bench_promise.c @@ -67,7 +67,7 @@ eina_bench_promise_sync_then(int request) eina_init(); - Eina_Promise_Owner* owner = eina_promise_value_add(sizeof(struct value_type)); + Eina_Promise_Owner* owner = eina_promise_add(); Eina_Promise* promise = eina_promise_owner_promise_get(owner); eina_promise_ref(promise); @@ -87,116 +87,6 @@ eina_bench_promise_sync_then(int request) eina_shutdown(); } -static void -eina_bench_promise_copy_value_set_after_then(int request) -{ - const char *tmp; - unsigned int j; - int i; - - eina_init(); - - struct value_type const v = {0, 0, 0, 0}; - - for (j = 0; j != 200; ++j) - for (i = 0; i != request; ++i) - { - Eina_Promise_Owner* owner = eina_promise_value_add(sizeof(struct value_type)); - Eina_Promise* promise = eina_promise_owner_promise_get(owner); - - eina_promise_then(promise, &cb, NULL, NULL); - eina_promise_owner_value_set(owner, &v, NULL); - } - - /* Suppress warnings as we really don't want to do anything. */ - (void) tmp; - - eina_shutdown(); -} - -static void -eina_bench_promise_no_copy_value_set_after_then(int request) -{ - const char *tmp; - unsigned int j; - int i; - - eina_init(); - - for (j = 0; j != 200; ++j) - for (i = 0; i != request; ++i) - { - Eina_Promise_Owner* owner = eina_promise_value_add(sizeof(struct value_type)); - Eina_Promise* promise = eina_promise_owner_promise_get(owner); - struct value_type* v = eina_promise_owner_buffer_get(owner); - - eina_promise_then(promise, &cb, NULL, NULL); - - v->x = v->y = v-> w = v->h = 0; - eina_promise_owner_value_set(owner, NULL, NULL); - } - - /* Suppress warnings as we really don't want to do anything. */ - (void) tmp; - - eina_shutdown(); -} - -static void -eina_bench_promise_no_copy_value_set_before_then(int request) -{ - const char *tmp; - unsigned int j; - int i; - - eina_init(); - - for (j = 0; j != 200; ++j) - for (i = 0; i != request; ++i) - { - Eina_Promise_Owner* owner = eina_promise_value_add(sizeof(struct value_type)); - Eina_Promise* promise = eina_promise_owner_promise_get(owner); - struct value_type* v = eina_promise_owner_buffer_get(owner); - - v->x = v->y = v-> w = v->h = 0; - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_promise_then(promise, &cb, NULL, NULL); - } - - /* Suppress warnings as we really don't want to do anything. */ - (void) tmp; - - eina_shutdown(); -} - -static void -eina_bench_promise_copy_value_set_before_then(int request) -{ - const char *tmp; - unsigned int j; - int i; - - eina_init(); - - struct value_type const v = {0, 0, 0, 0}; - - for (j = 0; j != 200; ++j) - for (i = 0; i != request; ++i) - { - Eina_Promise_Owner* owner = eina_promise_value_add(sizeof(struct value_type)); - Eina_Promise* promise = eina_promise_owner_promise_get(owner); - - eina_promise_then(promise, &cb, NULL, NULL); - eina_promise_owner_value_set(owner, &v, NULL); - } - - /* Suppress warnings as we really don't want to do anything. */ - (void) tmp; - - eina_shutdown(); -} - static void indirect_free(void* p) { free(p); @@ -398,18 +288,6 @@ void eina_bench_promise(Eina_Benchmark *bench) eina_benchmark_register(bench, "promise synchronous then", EINA_BENCHMARK( eina_bench_promise_sync_then), 100, 20100, 500); - eina_benchmark_register(bench, "promise copy value set after then", - EINA_BENCHMARK( - eina_bench_promise_copy_value_set_after_then), 100, 20100, 500); - eina_benchmark_register(bench, "promise copy value set before then", - EINA_BENCHMARK( - eina_bench_promise_copy_value_set_before_then), 100, 20100, 500); - eina_benchmark_register(bench, "promise no copy value set after then", - EINA_BENCHMARK( - eina_bench_promise_no_copy_value_set_after_then), 100, 20100, 500); - eina_benchmark_register(bench, "promise no copy value set before then", - EINA_BENCHMARK( - eina_bench_promise_no_copy_value_set_before_then), 100, 20100, 500); eina_benchmark_register(bench, "promise pointer value set after then mempool", EINA_BENCHMARK( eina_bench_promise_pointer_value_set_after_then_pooled), 100, 20100, 500); diff --git a/src/lib/ecore/ecore_thread_promise.c b/src/lib/ecore/ecore_thread_promise.c index 7798d36543..5e4fa112f2 100644 --- a/src/lib/ecore/ecore_thread_promise.c +++ b/src/lib/ecore/ecore_thread_promise.c @@ -108,14 +108,6 @@ static void _ecore_promise_thread_cancel(void* data, Ecore_Thread* thread EINA_U eina_promise_cancel(promise); } -static void* _ecore_promise_owner_buffer_get(_Ecore_Thread_Promise_Owner* promise) -{ - return promise->eina_owner->buffer_get(promise->eina_owner); -} -static size_t _ecore_promise_owner_value_size_get(_Ecore_Thread_Promise_Owner const* promise) -{ - return promise->eina_owner->value_size_get(promise->eina_owner); -} static void _ecore_promise_owner_value_set(_Ecore_Thread_Promise_Owner* promise, void* data, Eina_Promise_Free_Cb free) { promise->eina_owner->value_set(promise->eina_owner, data, free); @@ -191,16 +183,6 @@ static void _ecore_promise_unref(Eina_Promise const* promise) _Ecore_Thread_Promise_Owner* v = ECORE_PROMISE_GET_OWNER(promise); --v->ref_count; } -static void* _ecore_promise_buffer_get(Eina_Promise const* promise) -{ - _Ecore_Thread_Promise_Owner* v = ECORE_PROMISE_GET_OWNER(promise); - return v->eina_promise->buffer_get(v->eina_promise); -} -static size_t _ecore_promise_value_size_get(Eina_Promise const* promise) -{ - _Ecore_Thread_Promise_Owner* v = ECORE_PROMISE_GET_OWNER(promise); - return v->eina_promise->value_size_get(v->eina_promise); -} Ecore_Thread* ecore_thread_promise_run(Ecore_Thread_Promise_Cb func_blocking, Ecore_Thread_Promise_Cb func_cancel, @@ -216,8 +198,6 @@ Ecore_Thread* ecore_thread_promise_run(Ecore_Thread_Promise_Cb func_blocking, priv->owner_vtable.version = EINA_PROMISE_VERSION; priv->owner_vtable.value_set = EINA_FUNC_PROMISE_OWNER_VALUE_SET(&_ecore_promise_owner_value_set); priv->owner_vtable.error_set = EINA_FUNC_PROMISE_OWNER_ERROR_SET(&_ecore_promise_owner_error_set); - priv->owner_vtable.buffer_get = EINA_FUNC_PROMISE_OWNER_BUFFER_GET(&_ecore_promise_owner_buffer_get); - priv->owner_vtable.value_size_get = EINA_FUNC_PROMISE_OWNER_VALUE_SIZE_GET(&_ecore_promise_owner_value_size_get); priv->owner_vtable.promise_get = EINA_FUNC_PROMISE_OWNER_PROMISE_GET(&_ecore_thread_promise_owner_promise_get); priv->owner_vtable.pending_is = EINA_FUNC_PROMISE_OWNER_PENDING_IS(&_ecore_promise_owner_pending_is); priv->owner_vtable.cancelled_is = EINA_FUNC_PROMISE_OWNER_CANCELLED_IS(&_ecore_promise_owner_cancelled_is); @@ -233,8 +213,6 @@ Ecore_Thread* ecore_thread_promise_run(Ecore_Thread_Promise_Cb func_blocking, priv->promise_vtable.cancel = EINA_FUNC_PROMISE_CANCEL(&_ecore_promise_cancel); priv->promise_vtable.ref = EINA_FUNC_PROMISE_REF(&_ecore_promise_ref); priv->promise_vtable.unref = EINA_FUNC_PROMISE_UNREF(&_ecore_promise_unref); - priv->promise_vtable.value_size_get = EINA_FUNC_PROMISE_VALUE_SIZE_GET(&_ecore_promise_value_size_get); - priv->promise_vtable.buffer_get = EINA_FUNC_PROMISE_BUFFER_GET(&_ecore_promise_buffer_get); EINA_MAGIC_SET(&priv->promise_vtable, EINA_MAGIC_PROMISE); priv->thread_callback_data.data = data; diff --git a/src/lib/eina/eina_promise.c b/src/lib/eina/eina_promise.c index eac15173a5..36be3a279b 100644 --- a/src/lib/eina/eina_promise.c +++ b/src/lib/eina/eina_promise.c @@ -93,7 +93,6 @@ struct _Eina_Promise_Default Eina_Bool is_cancelled : 1; Eina_Bool is_manual_then : 1; Eina_Bool is_first_then : 1; - Eina_Bool is_pointer : 1; }; struct _Eina_Promise_Default_Owner @@ -101,7 +100,7 @@ struct _Eina_Promise_Default_Owner Eina_Promise_Owner owner_vtable; _Eina_Promise_Default promise; - char value[]; + void* pointer_value; }; #define EINA_PROMISE_GET_OWNER(p) (_Eina_Promise_Default_Owner*)((unsigned char*)p - offsetof(struct _Eina_Promise_Default_Owner, promise)) @@ -118,16 +117,15 @@ struct _Eina_Promise_Iterator } data; }; -typedef struct _Eina_Promise_Race_Value_Type _Eina_Promise_Race_Value_Type; -struct _Eina_Promise_Race_Value_Type +typedef struct _Eina_Promise_Race _Eina_Promise_Race; +struct _Eina_Promise_Race { - void* value; - unsigned int promise_index; + _Eina_Promise_Default_Owner promise_default; unsigned int num_promises; struct _Eina_Promise_Race_Information { Eina_Promise* promise; - _Eina_Promise_Default_Owner* self; + _Eina_Promise_Race* self; } promises[]; }; @@ -195,14 +193,7 @@ _eina_promise_then_calls(_Eina_Promise_Default_Owner* promise) } else if (callback->callback) { - if(promise->promise.is_pointer) - { - char* buffer = promise->value; - void** p = (void**)buffer; - (*callback->callback)(callback->data, *p); - } - else - (*callback->callback)(callback->data, &promise->value[0]); + (*callback->callback)(callback->data, promise->pointer_value); } free(callback); _eina_promise_unref(&promise->promise); @@ -243,14 +234,7 @@ _eina_promise_del(_Eina_Promise_Default_Owner* promise) if (promise->promise.value_free_cb) { - if(promise->promise.is_pointer) - { - char* buffer = promise->value; - void** p = (void**)buffer; - promise->promise.value_free_cb(*p); - } - else - promise->promise.value_free_cb((void*)&promise->value[0]); + promise->promise.value_free_cb(promise->pointer_value); } _eina_promise_free_callback_list(&promise->promise.progress_callbacks, @@ -262,49 +246,13 @@ _eina_promise_del(_Eina_Promise_Default_Owner* promise) free(promise); } -static void * -_eina_promise_owner_buffer_get(_Eina_Promise_Default_Owner* promise) -{ - return &promise->value[0]; -} - -static void * -_eina_promise_owner_pointer_buffer_get(_Eina_Promise_Default_Owner* promise) -{ - char* buffer = promise->value; - void** p = (void**)buffer; - return *p; -} - -static void * -_eina_promise_buffer_get(_Eina_Promise_Default const* promise) -{ - _Eina_Promise_Default_Owner const* p = EINA_PROMISE_GET_OWNER(promise); - return (void*)&p->value[0]; -} - static void * _eina_promise_value_get(_Eina_Promise_Default const* p) { _Eina_Promise_Default_Owner const* promise = EINA_PROMISE_GET_OWNER(p); if (p->has_finished && !p->has_errored) { - return (void*)&promise->value[0]; - } - else - { - return NULL; - } -} - -static void * -_eina_promise_pointer_value_get(_Eina_Promise_Default const* p) -{ - _Eina_Promise_Default_Owner const* promise = EINA_PROMISE_GET_OWNER(p); - if (p->has_finished && !p->has_errored) - { - char const* buffer = promise->value; - return *((void**)buffer); + return promise->pointer_value; } else { @@ -315,22 +263,7 @@ _eina_promise_pointer_value_get(_Eina_Promise_Default const* p) static void _eina_promise_owner_value_set(_Eina_Promise_Default_Owner* promise, const void* data, Eina_Promise_Free_Cb free) { - if (data && promise->promise.value_size) - { - memcpy(&promise->value[0], data, promise->promise.value_size); - } - - promise->promise.value_free_cb = free; - - _eina_promise_finish(promise); -} - -static void -_eina_promise_owner_pointer_value_set(_Eina_Promise_Default_Owner* promise, const void* data, Eina_Promise_Free_Cb free) -{ - char* buffer = promise->value; - void** p = (void**)buffer; - *p = (void*)data; + promise->pointer_value = (void*)data; promise->promise.value_free_cb = free; _eina_promise_finish(promise); } @@ -457,18 +390,6 @@ _eina_promise_cancel(_Eina_Promise_Default* promise) } } -static size_t -_eina_promise_value_size_get(_Eina_Promise_Default_Owner const* promise) -{ - return promise->promise.value_size; -} - -static size_t -_eina_promise_owner_value_size_get(_Eina_Promise_Default_Owner const* promise) -{ - return promise->promise.value_size; -} - static void _eina_promise_ref(_Eina_Promise_Default* p) { @@ -478,14 +399,16 @@ _eina_promise_ref(_Eina_Promise_Default* p) static void _eina_promise_unref(_Eina_Promise_Default* p) { - if (p->ref <= 1 && p->has_finished && p->can_be_deleted) + if (--p->ref <= 0 && p->has_finished && p->can_be_deleted) { _eina_promise_del(EINA_PROMISE_GET_OWNER(p)); } - else - { - --p->ref; - } +} + +static int +_eina_promise_ref_get(_Eina_Promise_Default* p) +{ + return p->ref; } static Eina_Promise * @@ -544,12 +467,8 @@ _eina_promise_owner_progress_notify(_Eina_Promise_Default_Owner* promise, Eina_P eina_inlist_append(promise->promise.progress_notify_callbacks, EINA_INLIST_GET(cb)); } -Eina_Promise_Owner * -eina_promise_value_add(int value_size) +static void eina_promise_add_internal(_Eina_Promise_Default_Owner* p) { - _Eina_Promise_Default_Owner* p; - - p = malloc(sizeof(_Eina_Promise_Default_Owner) + value_size); p->promise.vtable.version = EINA_PROMISE_VERSION; p->promise.vtable.then = EINA_FUNC_PROMISE_THEN(_eina_promise_then); p->promise.vtable.value_get = EINA_FUNC_PROMISE_VALUE_GET(_eina_promise_value_get); @@ -559,82 +478,29 @@ eina_promise_value_add(int value_size) p->promise.vtable.cancel = EINA_FUNC_PROMISE_CANCEL(_eina_promise_cancel); p->promise.vtable.ref = EINA_FUNC_PROMISE_REF(_eina_promise_ref); p->promise.vtable.unref = EINA_FUNC_PROMISE_UNREF(_eina_promise_unref); - p->promise.vtable.value_size_get = EINA_FUNC_PROMISE_VALUE_SIZE_GET(_eina_promise_value_size_get); - p->promise.vtable.buffer_get = EINA_FUNC_PROMISE_BUFFER_GET(_eina_promise_buffer_get); + p->promise.vtable.ref_get = EINA_FUNC_PROMISE_REF_GET(_eina_promise_ref_get); EINA_MAGIC_SET(&p->promise.vtable, EINA_MAGIC_PROMISE); - - p->promise.has_finished = p->promise.has_errored = - p->promise.is_cancelled = p->promise.is_manual_then = p->promise.is_pointer = EINA_FALSE; - p->promise.can_be_deleted = EINA_FALSE; + p->promise.is_first_then = EINA_TRUE; p->promise.ref = 1; - memset(&p->promise.then_callbacks, 0, sizeof(p->promise.then_callbacks)); - memset(&p->promise.progress_callbacks, 0, sizeof(p->promise.progress_callbacks)); - memset(&p->promise.progress_notify_callbacks, 0, sizeof(p->promise.progress_notify_callbacks)); - memset(&p->promise.cancel_callbacks, 0, sizeof(p->promise.cancel_callbacks)); - p->promise.value_size = value_size; - p->promise.value_free_cb = NULL; - p->promise.error = 0; p->owner_vtable.version = EINA_PROMISE_VERSION; p->owner_vtable.value_set = EINA_FUNC_PROMISE_OWNER_VALUE_SET(_eina_promise_owner_value_set); p->owner_vtable.error_set = EINA_FUNC_PROMISE_OWNER_ERROR_SET(_eina_promise_owner_error_set); - p->owner_vtable.buffer_get = EINA_FUNC_PROMISE_OWNER_BUFFER_GET(_eina_promise_owner_buffer_get); - p->owner_vtable.value_size_get = EINA_FUNC_PROMISE_OWNER_VALUE_SIZE_GET(_eina_promise_owner_value_size_get); p->owner_vtable.promise_get = EINA_FUNC_PROMISE_OWNER_PROMISE_GET(_eina_promise_owner_promise_get); p->owner_vtable.pending_is = EINA_FUNC_PROMISE_OWNER_PENDING_IS(_eina_promise_owner_pending_is); p->owner_vtable.cancelled_is = EINA_FUNC_PROMISE_OWNER_CANCELLED_IS(_eina_promise_owner_cancelled_is); p->owner_vtable.progress = EINA_FUNC_PROMISE_OWNER_PROGRESS(_eina_promise_owner_progress); p->owner_vtable.progress_notify = EINA_FUNC_PROMISE_OWNER_PROGRESS_NOTIFY(_eina_promise_owner_progress_notify); EINA_MAGIC_SET(&p->owner_vtable, EINA_MAGIC_PROMISE_OWNER); - - return &p->owner_vtable; } EAPI Eina_Promise_Owner * eina_promise_add() { _Eina_Promise_Default_Owner* p; - - p = malloc(sizeof(_Eina_Promise_Default_Owner) + sizeof(void*)); - p->promise.vtable.version = EINA_PROMISE_VERSION; - p->promise.vtable.then = EINA_FUNC_PROMISE_THEN(_eina_promise_then); - p->promise.vtable.value_get = EINA_FUNC_PROMISE_VALUE_GET(_eina_promise_pointer_value_get); - p->promise.vtable.error_get = EINA_FUNC_PROMISE_ERROR_GET(_eina_promise_error_get); - p->promise.vtable.pending_is = EINA_FUNC_PROMISE_PENDING_IS(_eina_promise_pending_is); - p->promise.vtable.progress_cb_add = EINA_FUNC_PROMISE_PROGRESS_CB_ADD(_eina_promise_progress_cb_add); - p->promise.vtable.cancel = EINA_FUNC_PROMISE_CANCEL(_eina_promise_cancel); - p->promise.vtable.ref = EINA_FUNC_PROMISE_REF(_eina_promise_ref); - p->promise.vtable.unref = EINA_FUNC_PROMISE_UNREF(_eina_promise_unref); - p->promise.vtable.value_size_get = EINA_FUNC_PROMISE_VALUE_SIZE_GET(_eina_promise_value_size_get); - p->promise.vtable.buffer_get = EINA_FUNC_PROMISE_BUFFER_GET(_eina_promise_buffer_get); - EINA_MAGIC_SET(&p->promise.vtable, EINA_MAGIC_PROMISE); - - p->promise.has_finished = p->promise.has_errored = - p->promise.is_cancelled = p->promise.is_manual_then = EINA_FALSE; - p->promise.is_first_then = p->promise.is_pointer = EINA_TRUE; - p->promise.can_be_deleted = EINA_FALSE; - p->promise.ref = 1; - memset(&p->promise.then_callbacks, 0, sizeof(p->promise.then_callbacks)); - memset(&p->promise.progress_callbacks, 0, sizeof(p->promise.progress_callbacks)); - memset(&p->promise.progress_notify_callbacks, 0, sizeof(p->promise.progress_notify_callbacks)); - memset(&p->promise.cancel_callbacks, 0, sizeof(p->promise.cancel_callbacks)); - p->promise.value_size = 0; - p->promise.value_free_cb = NULL; - p->promise.error = 0; - - p->owner_vtable.version = EINA_PROMISE_VERSION; - p->owner_vtable.value_set = EINA_FUNC_PROMISE_OWNER_VALUE_SET(_eina_promise_owner_pointer_value_set); - p->owner_vtable.error_set = EINA_FUNC_PROMISE_OWNER_ERROR_SET(_eina_promise_owner_error_set); - p->owner_vtable.buffer_get = EINA_FUNC_PROMISE_OWNER_BUFFER_GET(_eina_promise_owner_pointer_buffer_get); - p->owner_vtable.value_size_get = EINA_FUNC_PROMISE_OWNER_VALUE_SIZE_GET(_eina_promise_owner_value_size_get); - p->owner_vtable.promise_get = EINA_FUNC_PROMISE_OWNER_PROMISE_GET(_eina_promise_owner_promise_get); - p->owner_vtable.pending_is = EINA_FUNC_PROMISE_OWNER_PENDING_IS(_eina_promise_owner_pending_is); - p->owner_vtable.cancelled_is = EINA_FUNC_PROMISE_OWNER_CANCELLED_IS(_eina_promise_owner_cancelled_is); - p->owner_vtable.progress = EINA_FUNC_PROMISE_OWNER_PROGRESS(_eina_promise_owner_progress); - p->owner_vtable.progress_notify = EINA_FUNC_PROMISE_OWNER_PROGRESS_NOTIFY(_eina_promise_owner_progress_notify); - EINA_MAGIC_SET(&p->owner_vtable, EINA_MAGIC_PROMISE_OWNER); - + p = calloc(sizeof(_Eina_Promise_Default_Owner), 1); + eina_promise_add_internal(p); return &p->owner_vtable; } @@ -663,12 +529,13 @@ _eina_promise_all_compose_then_cb(void *data, void* value EINA_UNUSED) if (!promise->promise.has_finished) { - iterator = (_Eina_Promise_Iterator*)promise->value; - if (++iterator->data.promises_finished == iterator->data.num_promises) + iterator = promise->pointer_value; + if (++(iterator->data.promises_finished) == iterator->data.num_promises) { _eina_promise_finish(promise); } } + eina_promise_unref(&promise->promise.vtable); } static void @@ -676,12 +543,14 @@ _eina_promise_all_compose_error_then_cb(void *data, Eina_Error error) { _Eina_Promise_Default_Owner* promise = data; EINA_MAGIC_CHECK_PROMISE_OWNER(&promise->owner_vtable); + if (!promise->promise.has_finished) { promise->promise.has_finished = promise->promise.has_errored = EINA_TRUE; promise->promise.error = error; _eina_promise_finish(promise); } + eina_promise_unref(&promise->promise.vtable); } static void @@ -693,6 +562,8 @@ _eina_promise_all_free(_Eina_Promise_Iterator* value) { eina_promise_unref(value->data.promises[i]); } + + free(value); } Eina_Promise * @@ -715,19 +586,23 @@ eina_promise_all(Eina_Iterator* it) eina_iterator_free(it); - promise = (_Eina_Promise_Default_Owner*) - eina_promise_value_add(sizeof(_Eina_Promise_Iterator) + - sizeof(_Eina_Promise_Default_Owner*)*eina_array_count_get(promises)); - internal_it = (_Eina_Promise_Iterator*)&promise->value[0]; - _eina_promise_iterator_setup(internal_it, promises); + promise = (_Eina_Promise_Default_Owner*)eina_promise_add(); + internal_it = malloc(sizeof(_Eina_Promise_Iterator) + + sizeof(_Eina_Promise_Default_Owner*) * eina_array_count_get(promises)); promise->promise.value_free_cb = (Eina_Promise_Free_Cb)&_eina_promise_all_free; + promise->pointer_value = (void*)internal_it; + + _eina_promise_iterator_setup(internal_it, promises); + cur_promise = internal_it->data.promises; last = internal_it->data.promises + internal_it->data.num_promises; for (;cur_promise != last; ++cur_promise) { eina_promise_ref(*cur_promise); // We need to keep the value alive until this promise is freed + // We need to keep the all promise alive while there are callbacks registered to it + eina_promise_ref(&promise->promise.vtable); eina_promise_then(*cur_promise, &_eina_promise_all_compose_then_cb, &_eina_promise_all_compose_error_then_cb, promise); } @@ -813,7 +688,7 @@ eina_promise_progress_notification(Eina_Promise_Owner* promise) { Eina_Promise_Owner* owner; - owner = eina_promise_value_add(0); + owner = eina_promise_add(); eina_promise_owner_progress_notify(promise, &_eina_promise_progress_notify_fulfilled, owner, &_eina_promise_progress_notify_finish); @@ -822,13 +697,17 @@ eina_promise_progress_notification(Eina_Promise_Owner* promise) } // Race implementation -static void -_eina_promise_race_free(_Eina_Promise_Race_Value_Type* value) +static void _eina_promise_race_unref(_Eina_Promise_Race* p) { - unsigned i = 0; - for (;i != value->num_promises; ++i) + unsigned i; + if (--p->promise_default.promise.ref <= 0 && p->promise_default.promise.has_finished + && p->promise_default.promise.can_be_deleted) { - eina_promise_unref(value->promises[i].promise); + for(i = 0; i != p->num_promises; ++i) + { + eina_promise_unref(p->promises[i].promise); + } + _eina_promise_del(EINA_PROMISE_GET_OWNER(&p->promise_default)); } } @@ -836,45 +715,31 @@ static void _eina_promise_race_compose_then_cb(void *data, void* value EINA_UNUSED) { struct _Eina_Promise_Race_Information* info = data; - _Eina_Promise_Default_Owner* race_promise; - _Eina_Promise_Race_Value_Type *race_value; + _Eina_Promise_Race* race_promise = info->self; - race_promise = info->self; - race_value = (_Eina_Promise_Race_Value_Type*)race_promise->value; - - if (!race_promise->promise.has_finished) - { - race_value->value = value; - race_value->promise_index = info - &race_value->promises[0]; - _eina_promise_finish(race_promise); - } + if (!race_promise->promise_default.promise.has_finished) + eina_promise_owner_value_set(&race_promise->promise_default.owner_vtable, value, NULL); + eina_promise_unref(&race_promise->promise_default.promise.vtable); } static void _eina_promise_race_compose_error_then_cb(void *data, Eina_Error error) { struct _Eina_Promise_Race_Information* info = data; - _Eina_Promise_Default_Owner* race_promise; - _Eina_Promise_Race_Value_Type *race_value; + _Eina_Promise_Race* race_promise = info->self; - race_promise = info->self; - race_value = (_Eina_Promise_Race_Value_Type*)race_promise->value; - - if (!race_promise->promise.has_finished) - { - race_value->promise_index = info - &race_value->promises[0]; - eina_promise_owner_error_set(&race_promise->owner_vtable, error); - } + if (!race_promise->promise_default.promise.has_finished) + eina_promise_owner_error_set(&race_promise->promise_default.owner_vtable, error); + eina_promise_unref(&race_promise->promise_default.promise.vtable); } Eina_Promise * eina_promise_race(Eina_Iterator* it) { - _Eina_Promise_Default_Owner *promise; + _Eina_Promise_Race *promise; Eina_Promise* current; Eina_Array* promises; struct _Eina_Promise_Race_Information *cur_promise, *last; - _Eina_Promise_Race_Value_Type *value; int num_promises; EINA_SAFETY_ON_NULL_RETURN_VAL(it, NULL); @@ -889,30 +754,27 @@ eina_promise_race(Eina_Iterator* it) eina_iterator_free(it); num_promises = eina_array_count_get(promises); - promise = (_Eina_Promise_Default_Owner*) - eina_promise_value_add(sizeof(_Eina_Promise_Race_Value_Type) + - sizeof(struct _Eina_Promise_Race_Information)*num_promises); - value = eina_promise_owner_buffer_get((Eina_Promise_Owner*)promise); - value->value = NULL; - value->promise_index = -1; - value->num_promises = num_promises; + promise = calloc(sizeof(_Eina_Promise_Race) + sizeof(struct _Eina_Promise_Race_Information)*num_promises, 1); + eina_promise_add_internal(&promise->promise_default); - promise->promise.value_free_cb = (Eina_Promise_Free_Cb)&_eina_promise_race_free; + promise->num_promises = num_promises; + promise->promise_default.promise.vtable.unref = EINA_FUNC_PROMISE_UNREF(_eina_promise_race_unref); - cur_promise = value->promises; - last = value->promises + value->num_promises; + cur_promise = promise->promises; + last = promise->promises + num_promises; for (int i = 0;cur_promise != last; ++cur_promise, ++i) { cur_promise->promise = eina_array_data_get(promises, i); cur_promise->self = promise; eina_promise_ref(cur_promise->promise); // We need to keep the value alive until this promise is freed + // We need to keep the all promise alive while there are callbacks registered to it + eina_promise_ref(&promise->promise_default.promise.vtable); eina_promise_then(cur_promise->promise, &_eina_promise_race_compose_then_cb, &_eina_promise_race_compose_error_then_cb, cur_promise); } eina_array_free(promises); - - return &promise->promise.vtable; + return &promise->promise_default.promise.vtable; } // API functions @@ -1008,28 +870,12 @@ eina_promise_unref(Eina_Promise* promise) promise->unref(promise); } -EAPI void * -eina_promise_owner_buffer_get(Eina_Promise_Owner* promise) -{ - _EINA_PROMISE_NULL_CHECK(promise, NULL); - EINA_MAGIC_CHECK_PROMISE_OWNER(promise); - return promise->buffer_get(promise); -} - -EAPI void * -eina_promise_buffer_get(Eina_Promise* promise) -{ - _EINA_PROMISE_NULL_CHECK(promise, NULL); - EINA_MAGIC_CHECK_PROMISE(promise); - return promise->buffer_get(promise); -} - -EAPI size_t -eina_promise_value_size_get(Eina_Promise const* promise) +EAPI int +eina_promise_ref_get(Eina_Promise* promise) { _EINA_PROMISE_NULL_CHECK(promise, 0); EINA_MAGIC_CHECK_PROMISE(promise); - return promise->value_size_get(promise); + return promise->ref_get(promise); } EAPI Eina_Promise * diff --git a/src/lib/eina/eina_promise.h b/src/lib/eina/eina_promise.h index 63d356aaab..f0120467ea 100644 --- a/src/lib/eina/eina_promise.h +++ b/src/lib/eina/eina_promise.h @@ -99,6 +99,13 @@ typedef void(*Eina_Promise_Unref_Cb)(Eina_Promise* promise); #define EINA_FUNC_PROMISE_UNREF(Function) ((Eina_Promise_Unref_Cb)Function) +/* + * @brief Function callback type for promise's ref_get function override + */ +typedef int(*Eina_Promise_Ref_Get_Cb)(Eina_Promise* promise); + +#define EINA_FUNC_PROMISE_REF_GET(Function) ((Eina_Promise_Ref_Get_Cb)Function) + /* * @brief Function callback type for promise's buffer_get function override */ @@ -106,14 +113,6 @@ typedef void*(*Eina_Promise_Buffer_Get_Cb)(Eina_Promise* promise); #define EINA_FUNC_PROMISE_BUFFER_GET(Function) ((Eina_Promise_Buffer_Get_Cb)Function) -/* - * @brief Function callback type for promise's value_size_get function override - */ -typedef size_t(*Eina_Promise_Value_Size_Get_Cb)(Eina_Promise const* promise); - -#define EINA_FUNC_PROMISE_VALUE_SIZE_GET(Function) ((Eina_Promise_Value_Size_Get_Cb)Function) - - /* * @brief Function callback type for promise owner's buffer_get function override */ @@ -121,13 +120,6 @@ typedef void*(*Eina_Promise_Owner_Buffer_Get_Cb)(Eina_Promise_Owner* promise); #define EINA_FUNC_PROMISE_OWNER_BUFFER_GET(Function) ((Eina_Promise_Owner_Buffer_Get_Cb)Function) -/* - * @brief Function callback type for promise owner's value_size_get function override - */ -typedef size_t(*Eina_Promise_Owner_Value_Size_Get_Cb)(Eina_Promise_Owner const* promise); - -#define EINA_FUNC_PROMISE_OWNER_VALUE_SIZE_GET(Function) ((Eina_Promise_Owner_Value_Size_Get_Cb)Function) - /* * @brief Function callback type for promise owner's promise_get function override */ @@ -192,8 +184,7 @@ struct _Eina_Promise Eina_Promise_Cancel_Cb cancel; Eina_Promise_Ref_Cb ref; Eina_Promise_Unref_Cb unref; - Eina_Promise_Value_Size_Get_Cb value_size_get; - Eina_Promise_Buffer_Get_Cb buffer_get; + Eina_Promise_Ref_Get_Cb ref_get; #define EINA_MAGIC_PROMISE 0x07932A5B EINA_MAGIC; }; @@ -203,8 +194,6 @@ struct _Eina_Promise_Owner int version; Eina_Promise_Owner_Value_Set_Cb value_set; Eina_Promise_Owner_Error_Set_Cb error_set; - Eina_Promise_Owner_Buffer_Get_Cb buffer_get; - Eina_Promise_Owner_Value_Size_Get_Cb value_size_get; Eina_Promise_Owner_Promise_Get_Cb promise_get; Eina_Promise_Owner_Pending_Is_Cb pending_is; Eina_Promise_Owner_Cancelled_Is_Cb cancelled_is; @@ -282,33 +271,6 @@ EAPI void eina_promise_owner_value_set(Eina_Promise_Owner* promise, const void* */ EAPI void* eina_promise_value_get(Eina_Promise const* promise); -/* - * @brief Returns the pointer to the buffer that holds the value. - * - * If the promise is finished and has not failed, this function is the - * same as @eina_promise_value_get. Otherwise, instead of returning - * NULL as @eina_promise_value_get, this function always returns the - * buffer pointer to where the value will be hold. - * - * @param promise The promise for which to get the buffer pointer - * @return Buffer pointer - */ -EAPI void* eina_promise_buffer_get(Eina_Promise* promise); - -/* - * @brief Returns the pointer to the buffer that holds the value. - * - * This function always return the buffer pointer independently if the - * value has been set or not. This is useful to instantiate the value - * directly in the correct buffer, without needing to copy. Then the - * user can @eina_promise_owner_value_set with a NULL pointer for the - * value to avoid copying over the buffer. - * - * @param promise The promise owner for which to get the buffer pointer - * @return Buffer pointer - */ -EAPI void* eina_promise_owner_buffer_get(Eina_Promise_Owner* promise); - /* * @brief Sets an error to the Eina_Promise * @@ -331,14 +293,6 @@ EAPI void eina_promise_owner_error_set(Eina_Promise_Owner* promise, Eina_Error e */ EAPI Eina_Error eina_promise_error_get(Eina_Promise const* promise); -/* - * @brief Gets the size of the value in eina_promise_value_get. - * - * @param promise The promise for which to get the value size - * @return The size of the value in eina_promise_value_get. - */ -EAPI size_t eina_promise_value_size_get(Eina_Promise const* promise); - /* * @brief Returns @EINA_TRUE if the promise is still pending and * still waiting on a value to be set and @EINA_FALSE otherwise. @@ -445,31 +399,18 @@ EAPI void eina_promise_owner_progress_notify(Eina_Promise_Owner* promise, */ EAPI void eina_promise_unref(Eina_Promise* promise); +/* + * @brief Get the reference count for the Eina_Promise. + + * @param promise The promise for which to get its reference + */ +EAPI int eina_promise_ref_get(Eina_Promise* promise); + /* * @brief Function callback type when promise is canceled */ typedef void(*Eina_Promise_Default_Cancel_Cb)(void* data, Eina_Promise_Owner* promise); -/* - * @brief Creates a @Eina_Promise_Owner - * - * Create a @Eina_Promise_Owner with a value of size value_size. Which - * is a promise with ownership of the value to be set. It is used by - * the asynchronous operation to set the actual value when it becomes - * available. The Promise itself, returned by - * eina_promise_owner_promise_get, represents the asynchronicity of - * the value itself and is used solely to get the value and to handle - * users of the asynchronous value. That's why Promises have a - * reference count while Promise Owners do not, the - * eina_promise_owner_value_set must be done only once, and - * consequently, has a unique ownership of the owner lifetime, while - * the promise can be queried and used by multiple users. - * - * @param value_size Size of value-type that Eina_Promise will hold - * @return @Eina_Promise_Owner just instantiated - */ -EAPI Eina_Promise_Owner* eina_promise_value_add(int value_size); - /* * @brief Creates a @Eina_Promise_Owner * diff --git a/src/lib/eio/eio_job.c b/src/lib/eio/eio_job.c index a8fccdb96b..dd35f84eb6 100644 --- a/src/lib/eio/eio_job.c +++ b/src/lib/eio/eio_job.c @@ -168,6 +168,8 @@ _free_xattr_data(Eio_Xattr_Data *value) EINA_SAFETY_ON_NULL_RETURN(value); if (value->data) free((void*)value->data); + + free(value); } static void @@ -179,13 +181,12 @@ _file_done_data_cb(void *data, Eio_File *handler EINA_UNUSED, const char *attr_d EINA_SAFETY_ON_NULL_RETURN(operation); EINA_SAFETY_ON_NULL_RETURN(operation->promise); - ret_data = eina_promise_owner_buffer_get(operation->promise); - + ret_data = calloc(sizeof(Eio_Xattr_Data), 1); ret_data->data = calloc(sizeof(char), size + 1); strcpy((char*)ret_data->data, attr_data); ret_data->size = size; - eina_promise_owner_value_set(operation->promise, NULL, (Eina_Promise_Free_Cb)&_free_xattr_data); + eina_promise_owner_value_set(operation->promise, ret_data, (Eina_Promise_Free_Cb)&_free_xattr_data); _job_closure_del(operation); } @@ -318,7 +319,7 @@ _eio_job_file_direct_ls(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); _job_direct_ls_helper(&eio_file_direct_ls, obj, pd, path, promise); return eina_promise_owner_promise_get(promise); } @@ -328,7 +329,7 @@ _eio_job_file_stat_ls(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); _job_direct_ls_helper(&eio_file_stat_ls, obj, pd, path, promise); return eina_promise_owner_promise_get(promise); } @@ -338,7 +339,7 @@ _eio_job_dir_stat_ls(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); _job_direct_ls_helper(&eio_dir_stat_ls, obj, pd, path, promise); return eina_promise_owner_promise_get(promise); } @@ -348,7 +349,7 @@ _eio_job_dir_direct_ls(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); // Had to add the cast as dir_direct differs in the filter callback constness of one of // its arguments. _job_direct_ls_helper((Eio_Job_Direct_Ls_Func)&eio_dir_direct_ls, obj, pd, path, promise); @@ -360,7 +361,7 @@ _eio_job_file_ls(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); Job_Closure *operation_data = _job_closure_create(obj, pd, promise); Eina_Promise* p = eina_promise_owner_promise_get(promise); @@ -391,9 +392,10 @@ _file_stat_done_cb(void *data, Eio_File *handle EINA_UNUSED, const Eina_Stat *st EINA_SAFETY_ON_NULL_RETURN(operation); EINA_SAFETY_ON_NULL_RETURN(operation->promise); + Eina_Stat *my_stat = calloc(sizeof(Eina_Stat), 1); - // Placeholder value. We just want the callback to be called. - eina_promise_owner_value_set(operation->promise, stat, NULL); + *my_stat = *stat; + eina_promise_owner_value_set(operation->promise, my_stat, free); _job_closure_del(operation); } @@ -403,7 +405,7 @@ _eio_job_file_direct_stat(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(Eina_Stat)); + Eina_Promise_Owner* promise = eina_promise_add(); Job_Closure *operation_data = _job_closure_create(obj, pd, promise); Eina_Promise* p = eina_promise_owner_promise_get(promise); @@ -430,7 +432,7 @@ _eio_job_file_xattr_list_get(Eo *obj, Eio_Job_Data *pd, const char *path) { - Eina_Promise_Owner *promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner *promise = eina_promise_add(); Job_Closure *operation_data = _job_closure_create(obj, pd, promise); Eina_Promise* p = eina_promise_owner_promise_get(promise); @@ -461,7 +463,7 @@ _eio_job_file_xattr_set(Eo *obj, unsigned int xattr_size, Eina_Xattr_Flags flags) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(int)); + Eina_Promise_Owner* promise = eina_promise_add(); Job_Closure *operation_data = _job_closure_create(obj, pd, promise); Eina_Promise* p = eina_promise_owner_promise_get(promise); @@ -492,7 +494,7 @@ _eio_job_file_xattr_get(Eo *obj, const char *path, const char *attribute) { - Eina_Promise_Owner* promise = eina_promise_value_add(sizeof(Eio_Xattr_Data)); + Eina_Promise_Owner* promise = eina_promise_add(); Job_Closure *operation_data = _job_closure_create(obj, pd, promise); Eina_Promise* p = eina_promise_owner_promise_get(promise); diff --git a/src/lib/eio/eio_model.c b/src/lib/eio/eio_model.c index 8eba635092..fbf3f9b75e 100644 --- a/src/lib/eio/eio_model.c +++ b/src/lib/eio/eio_model.c @@ -41,7 +41,7 @@ _eio_stat_done_cb(void *data, Eio_File *handler EINA_UNUSED, const Eina_Stat *st Eina_List *l; EINA_LIST_FOREACH(priv->property_promises, l, p) { - Eina_Value* v = eina_promise_owner_buffer_get(p->promise); + Eina_Value* v = eina_value_new(EINA_VALUE_TYPE_CHAR); switch(p->property) { case EIO_MODEL_PROP_IS_DIR: @@ -64,7 +64,7 @@ _eio_stat_done_cb(void *data, Eio_File *handler EINA_UNUSED, const Eina_Stat *st break; }; - eina_promise_owner_value_set(p->promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + eina_promise_owner_value_set(p->promise, v, (Eina_Promise_Free_Cb)&eina_value_free); free(p); } eina_list_free(priv->property_promises); @@ -308,10 +308,9 @@ _eio_model_efl_model_property_get(Eo *obj EINA_UNUSED, Eio_Model_Data *priv, con case EIO_MODEL_PROP_PATH: case EIO_MODEL_PROP_MIME_TYPE: { - Eina_Value* v = eina_promise_owner_buffer_get(promise); - eina_value_setup(v, EINA_VALUE_TYPE_STRING); + Eina_Value* v = eina_value_new(EINA_VALUE_TYPE_STRING); eina_value_set(v, value); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + eina_promise_owner_value_set(promise, v, (Eina_Promise_Free_Cb)&eina_value_free); } break; default: @@ -382,8 +381,9 @@ _eio_model_efl_model_property_set(Eo *obj EINA_UNUSED, static void _eio_model_efl_model_children_count_get(Eo *obj EINA_UNUSED, Eio_Model_Data *priv, Eina_Promise_Owner *promise) { - unsigned int c = eina_list_count(priv->children_list); - eina_promise_owner_value_set(promise, &c, NULL); + unsigned int *c = calloc(sizeof(unsigned int), 1); + *c = eina_list_count(priv->children_list); + eina_promise_owner_value_set(promise, c, free); } static void diff --git a/src/lib/eldbus/eldbus_model_arguments.c b/src/lib/eldbus/eldbus_model_arguments.c index 91192c9411..05f3ce9eea 100644 --- a/src/lib/eldbus/eldbus_model_arguments.c +++ b/src/lib/eldbus/eldbus_model_arguments.c @@ -121,6 +121,7 @@ _eldbus_model_arguments_efl_model_property_set(Eo *obj EINA_UNUSED, Eina_Promise_Owner *promise) { Eina_Value *prop_value; + Eina_Value *promise_value; ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(property, promise, EFL_MODEL_ERROR_INCORRECT_VALUE); ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(value, promise, EFL_MODEL_ERROR_INCORRECT_VALUE); @@ -136,8 +137,10 @@ _eldbus_model_arguments_efl_model_property_set(Eo *obj EINA_UNUSED, eina_value_flush(prop_value); eina_value_copy(value, prop_value); - eina_value_copy(value, eina_promise_owner_buffer_get(promise)); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + + promise_value = eina_value_new(eina_value_type_get(value)); + eina_value_copy(value, promise_value); + eina_promise_owner_value_set(promise, promise_value, (Eina_Promise_Free_Cb)&eina_value_free); } static void @@ -146,6 +149,7 @@ _eldbus_model_arguments_efl_model_property_get(Eo *obj EINA_UNUSED, const char *property, Eina_Promise_Owner *promise) { + Eina_Value *promise_value; EINA_SAFETY_ON_NULL_RETURN(promise); ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(property, promise, EFL_MODEL_ERROR_INCORRECT_VALUE); @@ -159,8 +163,9 @@ _eldbus_model_arguments_efl_model_property_get(Eo *obj EINA_UNUSED, Eina_Bool ret = _eldbus_model_arguments_is_output_argument(pd, property); ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(ret, promise, EFL_MODEL_ERROR_PERMISSION_DENIED); - eina_value_copy(value, eina_promise_owner_buffer_get(promise)); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + promise_value = eina_value_new(eina_value_type_get(value)); + eina_value_copy(value, promise_value); + eina_promise_owner_value_set(promise, promise_value, (Eina_Promise_Free_Cb)&eina_value_free); } static Eo * @@ -191,8 +196,9 @@ _eldbus_model_arguments_efl_model_children_count_get(Eo *obj EINA_UNUSED, Eldbus_Model_Arguments_Data *pd EINA_UNUSED, Eina_Promise_Owner *promise) { - unsigned count = 0; - eina_promise_owner_value_set(promise, &count, NULL); + unsigned *count = malloc(sizeof(unsigned)); + *count = 0; + eina_promise_owner_value_set(promise, count, free); } static const char * diff --git a/src/lib/eldbus/eldbus_model_connection.c b/src/lib/eldbus/eldbus_model_connection.c index b05d9f7b34..e29eeb5116 100644 --- a/src/lib/eldbus/eldbus_model_connection.c +++ b/src/lib/eldbus/eldbus_model_connection.c @@ -114,10 +114,9 @@ _eldbus_model_connection_efl_model_property_get(Eo *obj EINA_UNUSED, pd->unique_name = strdup(unique_name); } - Eina_Value* v = eina_promise_owner_buffer_get(promise); - eina_value_setup(v, EINA_VALUE_TYPE_STRING); + Eina_Value* v = eina_value_new(EINA_VALUE_TYPE_STRING); eina_value_set(v, pd->unique_name); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + eina_promise_owner_value_set(promise, v, (Eina_Promise_Free_Cb)&eina_value_free); } static Eo * @@ -179,8 +178,9 @@ _eldbus_model_connection_efl_model_children_count_get(Eo *obj EINA_UNUSED, if (pd->is_listed) { - unsigned int c = eina_list_count(pd->children_list); - eina_promise_owner_value_set(promise, &c, NULL); + unsigned int *c = calloc(sizeof(unsigned int), 1); + *c = eina_list_count(pd->children_list); + eina_promise_owner_value_set(promise, c, free); return; } @@ -346,8 +346,9 @@ _eldbus_model_connection_names_list_cb(void *data, Eina_Promise_Owner *ep; EINA_LIST_FOREACH(pd->count_promises, i, ep) { - unsigned c = eina_list_count(pd->children_list); - eina_promise_owner_value_set(ep, &c, NULL); + unsigned *c = calloc(sizeof(unsigned), 1); + *c = eina_list_count(pd->children_list); + eina_promise_owner_value_set(ep, c, free); } eina_list_free(pd->count_promises); } diff --git a/src/lib/eldbus/eldbus_model_object.c b/src/lib/eldbus/eldbus_model_object.c index b2ab91e05f..d3cd86a0f6 100644 --- a/src/lib/eldbus/eldbus_model_object.c +++ b/src/lib/eldbus/eldbus_model_object.c @@ -149,10 +149,9 @@ _eldbus_model_object_efl_model_property_get(Eo *obj EINA_UNUSED, pd->unique_name = strdup(unique_name); } - Eina_Value* v = eina_promise_owner_buffer_get(promise); - eina_value_setup(v, EINA_VALUE_TYPE_STRING); + Eina_Value* v = eina_value_new(EINA_VALUE_TYPE_STRING); eina_value_set(v, pd->unique_name); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + eina_promise_owner_value_set(promise, v, (Eina_Promise_Free_Cb)&eina_value_free); } static Eo * @@ -208,8 +207,9 @@ _eldbus_model_object_efl_model_children_count_get(Eo *obj EINA_UNUSED, if (pd->is_listed) { - unsigned int c = eina_list_count(pd->children_list); - eina_promise_owner_value_set(promise, &c, NULL); + unsigned int *c = calloc(sizeof(unsigned int), 1); + *c = eina_list_count(pd->children_list); + eina_promise_owner_value_set(promise, c, free); return; } @@ -438,8 +438,9 @@ _eldbus_model_object_introspect_cb(void *data, Eina_Promise_Owner *ep; EINA_LIST_FOREACH(pd->count_promises, i, ep) { - unsigned c = eina_list_count(pd->children_list); - eina_promise_owner_value_set(ep, &c, NULL); + unsigned *c = calloc(sizeof(unsigned), 1); + *c = eina_list_count(pd->children_list); + eina_promise_owner_value_set(ep, c, free); } eina_list_free(pd->count_promises); diff --git a/src/lib/eldbus/eldbus_model_proxy.c b/src/lib/eldbus/eldbus_model_proxy.c index d6b104766f..1c75a8f7a1 100644 --- a/src/lib/eldbus/eldbus_model_proxy.c +++ b/src/lib/eldbus/eldbus_model_proxy.c @@ -163,6 +163,7 @@ _eldbus_model_proxy_efl_model_property_get(Eo *obj EINA_UNUSED, Eina_Promise_Owner *promise) { Eina_Bool ret; + Eina_Value *promise_value; EINA_SAFETY_ON_NULL_RETURN(promise); ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(property, promise, EFL_MODEL_ERROR_INCORRECT_VALUE); @@ -197,8 +198,9 @@ _eldbus_model_proxy_efl_model_property_get(Eo *obj EINA_UNUSED, ret = _eldbus_model_proxy_is_property_writeable(pd, property); ELDBUS_MODEL_ON_ERROR_EXIT_PROMISE_SET(ret, promise, EFL_MODEL_ERROR_READ_ONLY); - eina_value_copy(value, eina_promise_owner_buffer_get(promise)); - eina_promise_owner_value_set(promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + promise_value = eina_value_new(eina_value_type_get(value)); + eina_value_copy(value, promise_value); + eina_promise_owner_value_set(promise, promise_value, (Eina_Promise_Free_Cb)&eina_value_free); } static Eo * @@ -251,8 +253,9 @@ _eldbus_model_proxy_efl_model_children_count_get(Eo *obj EINA_UNUSED, pd->is_listed = EINA_TRUE; } - unsigned int c = eina_list_count(pd->children_list); - eina_promise_owner_value_set(promise, &c, NULL); + unsigned int *c = calloc(sizeof(unsigned int), 1); + *c = eina_list_count(pd->children_list); + eina_promise_owner_value_set(promise, c, free); } static void @@ -554,6 +557,7 @@ _eldbus_model_proxy_property_get_all_cb(void *data, const Eldbus_Message *msg, Eldbus_Pending *pending) { + Eina_Value *promise_value; Eldbus_Model_Proxy_Data *pd = (Eldbus_Model_Proxy_Data*)data; pd->pending_list = eina_list_remove(pd->pending_list, pending); @@ -592,8 +596,9 @@ _eldbus_model_proxy_property_get_all_cb(void *data, free(p->property); - eina_value_copy(value, eina_promise_owner_buffer_get(p->promise)); - eina_promise_owner_value_set(p->promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + promise_value = eina_value_new(eina_value_type_get(value)); + eina_value_copy(value, promise_value); + eina_promise_owner_value_set(p->promise, promise_value, (Eina_Promise_Free_Cb)&eina_value_free); } eina_list_free(pd->promise_list); @@ -651,6 +656,7 @@ _eldbus_model_proxy_property_set_cb(void *data, Eldbus_Model_Proxy_Data *pd = property_set_data->pd; const char *error_name, *error_text; Eina_Value *prop_value; + Eina_Value *promise_value; pd->pending_list = eina_list_remove(pd->pending_list, pending); @@ -675,8 +681,9 @@ _eldbus_model_proxy_property_set_cb(void *data, efl_model_property_changed_notify(pd->obj, property_set_data->property); } - eina_value_copy(prop_value, eina_promise_owner_buffer_get(property_set_data->promise)); - eina_promise_owner_value_set(property_set_data->promise, NULL, (Eina_Promise_Free_Cb)&eina_value_flush); + promise_value = eina_value_new(eina_value_type_get(prop_value)); + eina_value_copy(prop_value, promise_value); + eina_promise_owner_value_set(property_set_data->promise, promise_value, (Eina_Promise_Free_Cb)&eina_value_free); } else { diff --git a/src/tests/ecore/ecore_test_job.c b/src/tests/ecore/ecore_test_job.c index 2e1a528219..1306ea4694 100644 --- a/src/tests/ecore/ecore_test_job.c +++ b/src/tests/ecore/ecore_test_job.c @@ -21,7 +21,8 @@ START_TEST(ecore_test_job_promise) ecore_init(); - eina_promise_then(efl_loop_job(ecore_main_loop_get(), &bob), &_ecore_promise_quit, NULL, &bob); + Eina_Promise *promise = efl_loop_job(ecore_main_loop_get(), &bob); + eina_promise_then(promise, &_ecore_promise_quit, NULL, &bob); ecore_main_loop_begin(); diff --git a/src/tests/ecore/ecore_test_promise.c b/src/tests/ecore/ecore_test_promise.c index cf9c33f7df..3c7d8ebd8c 100644 --- a/src/tests/ecore/ecore_test_promise.c +++ b/src/tests/ecore/ecore_test_promise.c @@ -205,7 +205,7 @@ START_TEST(ecore_test_promise_normal_lifetime) ecore_init(); - promise_owner = eina_promise_value_add(0); + promise_owner = eina_promise_add(); promise = eina_promise_owner_promise_get(promise_owner); @@ -226,7 +226,7 @@ START_TEST(ecore_test_promise_normal_lifetime_all) ecore_init(); - promise_owner = eina_promise_value_add(0); + promise_owner = eina_promise_add(); first[0] = eina_promise_owner_promise_get(promise_owner); promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); @@ -252,7 +252,7 @@ START_TEST(ecore_test_promise_immediate_set_lifetime) ecore_init(); - owner = eina_promise_value_add(0); + owner = eina_promise_add(); promise = eina_promise_owner_promise_get(owner); eina_promise_owner_value_set(owner, NULL, NULL); @@ -272,7 +272,7 @@ START_TEST(ecore_test_promise_immediate_set_lifetime_all) ecore_init(); - owner = eina_promise_value_add(0); + owner = eina_promise_add(); first[0] = eina_promise_owner_promise_get(owner); promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); diff --git a/src/tests/eina/eina_suite.c b/src/tests/eina/eina_suite.c index 994d66d9df..3af23dac6a 100644 --- a/src/tests/eina/eina_suite.c +++ b/src/tests/eina/eina_suite.c @@ -26,59 +26,59 @@ #include "../efl_check.h" static const Efl_Test_Case etc[] = { - { "FixedPoint", eina_test_fp }, - { "Inarray", eina_test_inarray }, - { "Array", eina_test_array }, - { "Binary Share", eina_test_binshare }, - { "String Share", eina_test_stringshare }, - { "UString Share", eina_test_ustringshare }, - { "Log", eina_test_log }, - { "Error", eina_test_error }, - { "Magic", eina_test_magic }, - { "Inlist", eina_test_inlist }, - { "Lazy alloc", eina_test_lalloc }, - { "Main", eina_test_main }, - { "Counter", eina_test_counter }, - { "Hash", eina_test_hash }, - { "List", eina_test_list }, - { "CList", eina_test_clist }, - { "Iterator", eina_test_iterator }, - { "Accessor", eina_test_accessor }, - { "Module", eina_test_module }, - { "Convert", eina_test_convert }, - { "Rbtree", eina_test_rbtree }, - { "File", eina_test_file }, - { "Benchmark", eina_test_benchmark }, - { "Mempool", eina_test_mempool }, - { "Rectangle", eina_test_rectangle }, - { "Matrix Sparse", eina_test_matrixsparse }, - { "Eina Tiler", eina_test_tiler }, - { "Eina Strbuf", eina_test_strbuf }, - { "Eina Binbuf", eina_test_binbuf }, - { "String", eina_test_str }, - { "Unicode String", eina_test_ustr }, - { "QuadTree", eina_test_quadtree }, - { "Sched", eina_test_sched }, - { "Simple Xml Parser", eina_test_simple_xml_parser}, - { "Value", eina_test_value }, - { "COW", eina_test_cow }, - // Disabling Eina_Model test - // { "Model", eina_test_model }, - { "Barrier", eina_test_barrier }, - { "Tmp String", eina_test_tmpstr }, - { "Locking", eina_test_locking }, - { "ABI", eina_test_abi }, - { "Trash", eina_test_trash }, -#ifdef XATTR_TEST_DIR - { "Xattr", eina_test_xattr }, -#endif - { "Crc", eina_test_crc }, - { "Quad", eina_test_quad }, - { "Matrix", eina_test_matrix }, - { "Quaternion", eina_test_quaternion }, - { "Vector", eina_test_vector }, +/* { "FixedPoint", eina_test_fp }, */ +/* { "Inarray", eina_test_inarray }, */ +/* { "Array", eina_test_array }, */ +/* { "Binary Share", eina_test_binshare }, */ +/* { "String Share", eina_test_stringshare }, */ +/* { "UString Share", eina_test_ustringshare }, */ +/* { "Log", eina_test_log }, */ +/* { "Error", eina_test_error }, */ +/* { "Magic", eina_test_magic }, */ +/* { "Inlist", eina_test_inlist }, */ +/* { "Lazy alloc", eina_test_lalloc }, */ +/* { "Main", eina_test_main }, */ +/* { "Counter", eina_test_counter }, */ +/* { "Hash", eina_test_hash }, */ +/* { "List", eina_test_list }, */ +/* { "CList", eina_test_clist }, */ +/* { "Iterator", eina_test_iterator }, */ +/* { "Accessor", eina_test_accessor }, */ +/* { "Module", eina_test_module }, */ +/* { "Convert", eina_test_convert }, */ +/* { "Rbtree", eina_test_rbtree }, */ +/* { "File", eina_test_file }, */ +/* { "Benchmark", eina_test_benchmark }, */ +/* { "Mempool", eina_test_mempool }, */ +/* { "Rectangle", eina_test_rectangle }, */ +/* { "Matrix Sparse", eina_test_matrixsparse }, */ +/* { "Eina Tiler", eina_test_tiler }, */ +/* { "Eina Strbuf", eina_test_strbuf }, */ +/* { "Eina Binbuf", eina_test_binbuf }, */ +/* { "String", eina_test_str }, */ +/* { "Unicode String", eina_test_ustr }, */ +/* { "QuadTree", eina_test_quadtree }, */ +/* { "Sched", eina_test_sched }, */ +/* { "Simple Xml Parser", eina_test_simple_xml_parser}, */ +/* { "Value", eina_test_value }, */ +/* { "COW", eina_test_cow }, */ +/* // Disabling Eina_Model test */ +/* // { "Model", eina_test_model }, */ +/* { "Barrier", eina_test_barrier }, */ +/* { "Tmp String", eina_test_tmpstr }, */ +/* { "Locking", eina_test_locking }, */ +/* { "ABI", eina_test_abi }, */ +/* { "Trash", eina_test_trash }, */ +/* #ifdef XATTR_TEST_DIR */ +/* { "Xattr", eina_test_xattr }, */ +/* #endif */ +/* { "Crc", eina_test_crc }, */ +/* { "Quad", eina_test_quad }, */ +/* { "Matrix", eina_test_matrix }, */ +/* { "Quaternion", eina_test_quaternion }, */ +/* { "Vector", eina_test_vector }, */ { "Promise", eina_test_promise }, - { "Bezier", eina_test_bezier }, + /* { "Bezier", eina_test_bezier }, */ { NULL, NULL } }; diff --git a/src/tests/eina/eina_test_promise.c b/src/tests/eina/eina_test_promise.c index 086b6d5c73..5c73dba0da 100644 --- a/src/tests/eina/eina_test_promise.c +++ b/src/tests/eina/eina_test_promise.c @@ -37,127 +37,12 @@ _eina_test_promise_cb(void* data, void* value EINA_UNUSED) *(Eina_Bool*)data = EINA_TRUE; } -START_TEST(eina_test_promise_normal_lifetime) -{ - Eina_Promise_Owner* promise_owner; - Eina_Promise* promise; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - promise_owner = eina_promise_value_add(0); - - promise = eina_promise_owner_promise_get(promise_owner); - - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); - eina_promise_owner_value_set(promise_owner, NULL, NULL); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_normal_lifetime_all) -{ - Eina_Promise_Owner* promise_owner; - Eina_Promise* first[2] = {NULL, NULL}; - Eina_Promise* promise; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - promise_owner = eina_promise_value_add(0); - first[0] = eina_promise_owner_promise_get(promise_owner); - promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); - - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); - eina_promise_owner_value_set(promise_owner, NULL, NULL); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST - static void _eina_test_error_cb(void *data, Eina_Error error) { *(int *)data = error; } -START_TEST(eina_test_promise_error_set) -{ - Eina_Promise_Owner* promise_owner; - Eina_Promise* promise; - int ran = 0; - int error = 0xdeadbeef; - - eina_init(); - - promise_owner = eina_promise_value_add(0); - - promise = eina_promise_owner_promise_get(promise_owner); - - eina_promise_ref(promise); - - eina_promise_then(promise, NULL, &_eina_test_error_cb, &ran); - - eina_promise_owner_error_set(promise_owner, error); - - ck_assert(ran == error); - ck_assert_int_eq(error, eina_promise_error_get(promise)); - ck_assert(!eina_promise_pending_is(promise)); - ck_assert(!eina_promise_owner_cancelled_is(promise_owner)); - - eina_promise_unref(promise); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_immediate_set_lifetime) -{ - Eina_Promise_Owner* owner; - Eina_Promise* promise; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - owner = eina_promise_value_add(0); - promise = eina_promise_owner_promise_get(owner); - - eina_promise_owner_value_set(owner, NULL, NULL); - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_immediate_set_lifetime_all) -{ - Eina_Promise_Owner* owner; - Eina_Promise* first[2] = {NULL, NULL}; - Eina_Promise* promise; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - owner = eina_promise_value_add(0); - first[0] = eina_promise_owner_promise_get(owner); - promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); - - eina_promise_owner_value_set(owner, NULL, NULL); - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST - static void _eina_test_promise_value_all_cb(void* data, void* value) { Eina_Iterator* iterator = value; @@ -178,37 +63,6 @@ static void _eina_test_promise_value_all_cb(void* data, void* value) *(Eina_Bool*)data = EINA_TRUE; } -START_TEST(eina_test_promise_values_all) -{ - Eina_Promise_Owner* owners[2]; - Eina_Promise* promises[3] = {NULL, NULL, NULL}; - Eina_Promise* promise_all; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - int i = 10, j = 15; - - owners[0] = eina_promise_value_add(sizeof(int)); - owners[1] = eina_promise_value_add(sizeof(int)); - - promises[0] = eina_promise_owner_promise_get(owners[0]); - promises[1] = eina_promise_owner_promise_get(owners[1]); - - - promise_all = eina_promise_all(eina_carray_iterator_new((void**)&promises[0])); - - eina_promise_owner_value_set(owners[0], &i, NULL); - eina_promise_owner_value_set(owners[1], &j, NULL); - - eina_promise_then(promise_all, &_eina_test_promise_value_all_cb, NULL, &ran); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST - static void cancel_callback(void* data, Eina_Promise_Owner* promise EINA_UNUSED) { *(Eina_Bool*)data = EINA_TRUE; @@ -219,35 +73,6 @@ static void _cancel_promise_callback(void* data EINA_UNUSED, Eina_Error error EI *(Eina_Bool*)data = EINA_TRUE; } -START_TEST(eina_test_promise_cancel_promise) -{ - Eina_Bool ran = EINA_FALSE, cancel_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - eina_promise_owner_default_cancel_cb_add(owner, &cancel_callback, &cancel_ran, NULL); - - promise = eina_promise_owner_promise_get(owner); - - eina_promise_then(promise, NULL, &_cancel_promise_callback, &ran); - - eina_promise_cancel(promise); - - ck_assert(cancel_ran && ran); - ck_assert(eina_promise_owner_cancelled_is(owner)); - ck_assert(!eina_promise_pending_is(promise)); - ck_assert_int_eq(EINA_ERROR_PROMISE_CANCEL, eina_promise_error_get(promise)); - - // Finally free the owner - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - static void _cancel_then_callback(void *data, void *value EINA_UNUSED) { @@ -260,84 +85,6 @@ _cancel_error_callback(void *data, Eina_Error error EINA_UNUSED) *(int*)data = -1; } -START_TEST(eina_test_promise_cancel_finished_promise) -{ - Eina_Bool cancel_ran = EINA_FALSE; - int ran = 0; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - eina_promise_owner_default_cancel_cb_add(owner, &cancel_callback, &cancel_ran, NULL); - - promise = eina_promise_owner_promise_get(owner); - - eina_promise_then(promise, &_cancel_then_callback, &_cancel_error_callback, &ran); - - eina_promise_ref(promise); - eina_promise_owner_value_set(owner, NULL, NULL); - - ck_assert(!cancel_ran); - ck_assert_int_eq(1, ran); - ck_assert(!eina_promise_owner_cancelled_is(owner)); - ck_assert(!eina_promise_pending_is(promise)); - ck_assert_int_eq(0, eina_promise_error_get(promise)); - - eina_promise_cancel(promise); - - // The conditions should not have been changed. - ck_assert(!cancel_ran); - ck_assert_int_eq(1, ran); - ck_assert(!eina_promise_owner_cancelled_is(owner)); - ck_assert(!eina_promise_pending_is(promise)); - ck_assert_int_eq(0, eina_promise_error_get(promise)); - - eina_promise_unref(promise); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_double_cancel_promise) -{ - Eina_Bool ran = EINA_FALSE, cancel_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - eina_promise_owner_default_cancel_cb_add(owner, &cancel_callback, &cancel_ran, NULL); - - promise = eina_promise_owner_promise_get(owner); - - eina_promise_then(promise, NULL, &_cancel_promise_callback, &ran); - - eina_promise_cancel(promise); - - ck_assert(cancel_ran && ran); - ck_assert(eina_promise_owner_cancelled_is(owner)); - ck_assert(!eina_promise_pending_is(promise)); - ck_assert_int_eq(EINA_ERROR_PROMISE_CANCEL, eina_promise_error_get(promise)); - - cancel_ran = EINA_FALSE; - ran = EINA_FALSE; - - eina_promise_cancel(promise); - - ck_assert(!cancel_ran && !ran); - ck_assert(eina_promise_owner_cancelled_is(owner)); - ck_assert(!eina_promise_pending_is(promise)); - - // Finally free the owner - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - void progress_callback(void* data, void* value) { int* i = value; @@ -345,84 +92,12 @@ void progress_callback(void* data, void* value) *(Eina_Bool*)data = EINA_TRUE; } -START_TEST(eina_test_promise_progress) -{ - Eina_Bool progress_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - int i = 1; - - eina_init(); - - owner = eina_promise_value_add(0); - - promise = eina_promise_owner_promise_get(owner); - eina_promise_progress_cb_add(promise, &progress_callback, &progress_ran, NULL); - - eina_promise_owner_progress(owner, &i); - - ck_assert(progress_ran); - - eina_promise_unref(promise); - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - static void progress_notify(void* data, Eina_Promise_Owner* promise EINA_UNUSED) { ck_assert(!*(Eina_Bool*)data); *(Eina_Bool*)data = EINA_TRUE; } -START_TEST(eina_test_promise_progress_notify1) -{ - Eina_Bool progress_notify_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - eina_promise_owner_progress_notify(owner, &progress_notify, &progress_notify_ran, NULL); - - promise = eina_promise_owner_promise_get(owner); - eina_promise_progress_cb_add(promise, &progress_callback, NULL, NULL); // never run - eina_promise_progress_cb_add(promise, &progress_callback, NULL, NULL); // never run - - ck_assert(progress_notify_ran); - - eina_promise_unref(promise); - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_progress_notify2) -{ - Eina_Bool progress_notify_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - eina_promise_owner_progress_notify(owner, &progress_notify, &progress_notify_ran, NULL); - - promise = eina_promise_owner_promise_get(owner); - eina_promise_then(promise, NULL, &_cancel_promise_callback, NULL); // never run - eina_promise_then(promise, NULL, &_cancel_promise_callback, NULL); // never run - - ck_assert(progress_notify_ran); - - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - static void _eina_promise_progress_notify_fulfilled(void* data, void* value EINA_UNUSED) { @@ -434,71 +109,6 @@ _eina_promise_progress_notify_error(void* data EINA_UNUSED, Eina_Error error EIN { ck_assert(EINA_FALSE); } - -START_TEST(eina_test_promise_progress_notify3) -{ - Eina_Bool progress_notify_ran = EINA_FALSE; - Eina_Promise_Owner* owner; - Eina_Promise* promise; - Eina_Promise* promise_progress; - - eina_init(); - - owner = eina_promise_value_add(0); - promise_progress = eina_promise_progress_notification(owner); - eina_promise_then(promise_progress, &_eina_promise_progress_notify_fulfilled, - &_eina_promise_progress_notify_error, &progress_notify_ran); - - promise = eina_promise_owner_promise_get(owner); - eina_promise_progress_cb_add(promise, &progress_callback, NULL, NULL); // never run - eina_promise_progress_cb_add(promise, &progress_callback, NULL, NULL); // never run - - ck_assert(progress_notify_ran); - - eina_promise_unref(promise); - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_ignored) -{ - Eina_Promise_Owner* owner; - Eina_Promise* promise; - - eina_init(); - - owner = eina_promise_value_add(0); - promise = eina_promise_owner_promise_get(owner); - eina_promise_unref(promise); - eina_promise_owner_value_set(owner, NULL, NULL); - - eina_shutdown(); -} -END_TEST - -START_TEST(eina_test_promise_race) -{ - Eina_Promise_Owner* promise_owner; - Eina_Promise* first[2] = {NULL, NULL}; - Eina_Promise* promise; - Eina_Bool ran = EINA_FALSE; - - eina_init(); - - promise_owner = eina_promise_value_add(0); - first[0] = eina_promise_owner_promise_get(promise_owner); - promise = eina_promise_race(eina_carray_iterator_new((void**)&first[0])); - - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); - eina_promise_owner_value_set(promise_owner, NULL, NULL); - - ck_assert(ran == EINA_TRUE); - - eina_shutdown(); -} -END_TEST // pointers START_TEST(eina_test_pointer_promise_normal_lifetime) @@ -563,7 +173,37 @@ START_TEST(eina_test_pointer_promise_error_set) eina_promise_owner_error_set(promise_owner, error); - ck_assert(ran == error); + ck_assert_int_eq(error, ran); + ck_assert_int_eq(error, eina_promise_error_get(promise)); + ck_assert(!eina_promise_pending_is(promise)); + ck_assert(!eina_promise_owner_cancelled_is(promise_owner)); + + eina_promise_unref(promise); + + eina_shutdown(); +} +END_TEST + +START_TEST(eina_test_pointer_promise_error_set_all) +{ + Eina_Promise_Owner* promise_owner; + Eina_Promise* first[2] = {NULL, NULL}; + Eina_Promise* promise; + int ran = 0; + int error = 0xdeadbeef; + + eina_init(); + + promise_owner = eina_promise_add(0); + first[0] = eina_promise_owner_promise_get(promise_owner); + promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); + + eina_promise_ref(promise); + + eina_promise_then(promise, NULL, &_eina_test_error_cb, &ran); + eina_promise_owner_error_set(promise_owner, error); + + ck_assert_int_eq(error, ran); ck_assert_int_eq(error, eina_promise_error_get(promise)); ck_assert(!eina_promise_pending_is(promise)); ck_assert(!eina_promise_owner_cancelled_is(promise_owner)); @@ -616,6 +256,34 @@ START_TEST(eina_test_pointer_promise_immediate_set_lifetime_all) } END_TEST +START_TEST(eina_test_pointer_promise_manual_then) +{ + Eina_Promise_Owner* promise_owner; + Eina_Promise* promise; + Eina_Bool ran = EINA_FALSE; + + eina_init(); + + promise_owner = eina_promise_add(); + + eina_promise_owner_default_manual_then_set(promise_owner, EINA_TRUE); + + promise = eina_promise_owner_promise_get(promise_owner); + + eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); + + eina_promise_owner_value_set(promise_owner, NULL, NULL); + + ck_assert(!ran); + + eina_promise_owner_default_call_then(promise_owner); + + ck_assert(ran); + + eina_shutdown(); +} +END_TEST + START_TEST(eina_test_pointer_promise_values_all) { Eina_Promise_Owner* owners[2]; @@ -873,12 +541,20 @@ START_TEST(eina_test_pointer_promise_ignored) } END_TEST +static void +_eina_test_promise_race_cb(void* data, void* value EINA_UNUSED) +{ + *(Eina_Bool*)data = EINA_TRUE; + ck_assert_int_eq(*(int*)value, 42); +} + START_TEST(eina_test_pointer_promise_race) { Eina_Promise_Owner* promise_owner; Eina_Promise* first[2] = {NULL, NULL}; Eina_Promise* promise; Eina_Bool ran = EINA_FALSE; + int v = 42; eina_init(); @@ -886,10 +562,121 @@ START_TEST(eina_test_pointer_promise_race) first[0] = eina_promise_owner_promise_get(promise_owner); promise = eina_promise_race(eina_carray_iterator_new((void**)&first[0])); - eina_promise_then(promise, &_eina_test_promise_cb, NULL, &ran); + eina_promise_then(promise, &_eina_test_promise_race_cb, NULL, &ran); + eina_promise_owner_value_set(promise_owner, &v, NULL); + + ck_assert(!!ran); + + eina_shutdown(); +} +END_TEST + +START_TEST(eina_test_pointer_promise_race_error) +{ + Eina_Promise_Owner* promise_owner; + Eina_Promise* first[2] = {NULL, NULL}; + Eina_Promise* promise; + int ran = 0; + int error = 0xdeadbeef; + + eina_init(); + + promise_owner = eina_promise_add(); + first[0] = eina_promise_owner_promise_get(promise_owner); + promise = eina_promise_race(eina_carray_iterator_new((void**)&first[0])); + + eina_promise_ref(promise); + + eina_promise_then(promise, NULL, &_eina_test_error_cb, &ran); + eina_promise_owner_error_set(promise_owner, error); + + ck_assert_int_eq(error, ran); + ck_assert_int_eq(error, eina_promise_error_get(promise)); + ck_assert(!eina_promise_pending_is(promise)); + ck_assert(!eina_promise_owner_cancelled_is(promise_owner)); + + eina_promise_unref(promise); + + eina_shutdown(); +} +END_TEST + +// Null promises +START_TEST(eina_test_promise_error_promise_null_with_cb) +{ + int ran = 0; + eina_init(); + + eina_promise_then(NULL, NULL, _eina_test_error_cb, &ran); + + ck_assert_int_eq(EINA_ERROR_PROMISE_NULL, ran); + + eina_shutdown(); +} +END_TEST + +START_TEST(eina_test_promise_error_promise_null_without_cb) +{ + eina_init(); + + eina_promise_then(NULL, NULL, NULL, NULL); + + ck_assert_int_eq(EINA_ERROR_PROMISE_NULL, eina_error_get()); + + eina_shutdown(); +} +END_TEST + +START_TEST(eina_test_promise_error_promise_all_unref) +{ + Eina_Promise_Owner* promise_owner; + Eina_Promise* first[2] = {NULL, NULL}; + Eina_Promise* promise; + + eina_init(); + + promise_owner = eina_promise_add(); + first[0] = eina_promise_owner_promise_get(promise_owner); + promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); + + eina_promise_unref(promise); + eina_promise_owner_value_set(promise_owner, NULL, NULL); - ck_assert(ran == EINA_TRUE); + eina_shutdown(); +} +END_TEST + +static void _eina_test_promise_all_cb_lifetime_cb(void* data, Eina_Error error EINA_UNUSED) +{ + Eina_Promise* promise = data; + ck_assert_int_eq(eina_promise_ref_get(promise), 4); +} + +START_TEST(eina_test_promise_error_all_cb_lifetime) +{ + Eina_Promise_Owner* promise_owner[2]; + Eina_Promise* first[3] = {NULL, NULL, NULL}; + Eina_Promise* promise; + + eina_init(); + + promise_owner[0] = eina_promise_add(); + promise_owner[1] = eina_promise_add(); + first[0] = eina_promise_owner_promise_get(promise_owner[0]); + first[1] = eina_promise_owner_promise_get(promise_owner[1]); + promise = eina_promise_all(eina_carray_iterator_new((void**)&first[0])); + + ck_assert_int_eq(eina_promise_ref_get(promise), 3); + eina_promise_then(promise, NULL, &_eina_test_promise_all_cb_lifetime_cb, promise); + ck_assert_int_eq(eina_promise_ref_get(promise), 3); + + eina_promise_owner_error_set(promise_owner[0], EINA_ERROR_PROMISE_CANCEL); + + ck_assert_int_eq(eina_promise_ref_get(promise), 1); + + eina_promise_owner_value_set(promise_owner[1], NULL, NULL); + ck_assert_int_eq(eina_promise_ref_get(promise), 0); eina_shutdown(); } @@ -898,28 +685,14 @@ END_TEST void eina_test_promise(TCase *tc) { - tcase_add_test(tc, eina_test_promise_normal_lifetime); - tcase_add_test(tc, eina_test_promise_normal_lifetime_all); - tcase_add_test(tc, eina_test_promise_error_set); - /* tcase_add_test(tc, eina_test_promise_error_set_all); */ - tcase_add_test(tc, eina_test_promise_immediate_set_lifetime); - tcase_add_test(tc, eina_test_promise_immediate_set_lifetime_all); - tcase_add_test(tc, eina_test_promise_values_all); - tcase_add_test(tc, eina_test_promise_cancel_promise); - tcase_add_test(tc, eina_test_promise_cancel_finished_promise); - tcase_add_test(tc, eina_test_promise_double_cancel_promise); - tcase_add_test(tc, eina_test_promise_progress); - tcase_add_test(tc, eina_test_promise_progress_notify1); - tcase_add_test(tc, eina_test_promise_progress_notify2); - tcase_add_test(tc, eina_test_promise_progress_notify3); - tcase_add_test(tc, eina_test_promise_ignored); - tcase_add_test(tc, eina_test_promise_race); - // pointer + /* // pointer */ tcase_add_test(tc, eina_test_pointer_promise_normal_lifetime); tcase_add_test(tc, eina_test_pointer_promise_normal_lifetime_all); tcase_add_test(tc, eina_test_pointer_promise_error_set); + tcase_add_test(tc, eina_test_pointer_promise_error_set_all); tcase_add_test(tc, eina_test_pointer_promise_immediate_set_lifetime); tcase_add_test(tc, eina_test_pointer_promise_immediate_set_lifetime_all); + tcase_add_test(tc, eina_test_pointer_promise_manual_then); tcase_add_test(tc, eina_test_pointer_promise_values_all); tcase_add_test(tc, eina_test_pointer_promise_cancel_promise); tcase_add_test(tc, eina_test_pointer_promise_cancel_finished_promise); @@ -930,4 +703,13 @@ eina_test_promise(TCase *tc) tcase_add_test(tc, eina_test_pointer_promise_progress_notify3); tcase_add_test(tc, eina_test_pointer_promise_ignored); tcase_add_test(tc, eina_test_pointer_promise_race); + tcase_add_test(tc, eina_test_pointer_promise_race_error); + + // Null promises + tcase_add_test(tc, eina_test_promise_error_promise_null_with_cb); + tcase_add_test(tc, eina_test_promise_error_promise_null_without_cb); + tcase_add_test(tc, eina_test_promise_error_promise_all_unref); + + // Reference of composite promises + tcase_add_test(tc, eina_test_promise_error_all_cb_lifetime); }