forked from enlightenment/efl
remove elgacy ecore event usage in futures that limit to mainloop only
also eina_procmis was not threadsafe so cannto use loops in different threads at all until this was made safe. needed to disable the old ecore_event using code in for ecore futures and create a new efl loop message future and handler instead ... but now a quick experiment with multiple loops in 10 threads plus mainloop have timers at least work. i need to test more like fd handlers etc etc. but it's a step.
This commit is contained in:
parent
6ccfea3d51
commit
b27ca559f6
|
@ -38,6 +38,8 @@ ecore_eolian_files_public = \
|
|||
|
||||
ecore_eolian_files = \
|
||||
$(ecore_eolian_files_public) \
|
||||
lib/ecore/efl_loop_message_future_handler.eo \
|
||||
lib/ecore/efl_loop_message_future.eo \
|
||||
lib/ecore/efl_promise.eo \
|
||||
lib/ecore/efl_model_item.eo \
|
||||
lib/ecore/efl_model_container.eo \
|
||||
|
@ -97,6 +99,8 @@ lib/ecore/efl_loop_fd.c \
|
|||
lib/ecore/efl_loop_handler.c \
|
||||
lib/ecore/efl_loop_message.c \
|
||||
lib/ecore/efl_loop_message_handler.c \
|
||||
lib/ecore/efl_loop_message_future.c \
|
||||
lib/ecore/efl_loop_message_future_handler.c \
|
||||
lib/ecore/efl_io_closer_fd.c \
|
||||
lib/ecore/efl_io_positioner_fd.c \
|
||||
lib/ecore/efl_io_reader_fd.c \
|
||||
|
|
|
@ -32,6 +32,9 @@
|
|||
#include "ecore_event_message.eo.h"
|
||||
#include "ecore_event_message_handler.eo.h"
|
||||
|
||||
#include "efl_loop_message_future.eo.h"
|
||||
#include "efl_loop_message_future_handler.eo.h"
|
||||
|
||||
/**
|
||||
* @ingroup Ecore_MainLoop_Group
|
||||
*
|
||||
|
|
|
@ -12,16 +12,16 @@ typedef struct _Ecore_Future_Schedule_Entry
|
|||
Eina_Future_Schedule_Entry base;
|
||||
Eina_Future_Scheduler_Cb cb;
|
||||
Eina_Future *future;
|
||||
Ecore_Event *event;
|
||||
Eo *event;
|
||||
Eina_Value value;
|
||||
} Ecore_Future_Schedule_Entry;
|
||||
|
||||
//////
|
||||
// XXX: still using legacy ecore events
|
||||
static Ecore_Event_Handler *future_handler = NULL;
|
||||
//static Ecore_Event_Handler *future_handler = NULL;
|
||||
static Eina_Bool shutting_down = EINA_FALSE;
|
||||
static Eina_Mempool *mp_future_schedule_entry = NULL;
|
||||
static int ECORE_EV_FUTURE_ID = -1;
|
||||
//static int ECORE_EV_FUTURE_ID = -1;
|
||||
//
|
||||
//////
|
||||
|
||||
|
@ -71,17 +71,6 @@ ecore_event_add(int type,
|
|||
return (Ecore_Event *)msg;
|
||||
}
|
||||
|
||||
static void
|
||||
_event_del_cb(void *data, const Efl_Event *ev)
|
||||
{
|
||||
Ecore_Future_Schedule_Entry *entry = data;
|
||||
if ((ev->object == (Eo *) entry->event) && entry->future)
|
||||
{
|
||||
eina_future_cancel(entry->future);
|
||||
eina_value_flush(&entry->value);
|
||||
}
|
||||
}
|
||||
|
||||
EAPI void *
|
||||
ecore_event_del(Ecore_Event *event)
|
||||
{
|
||||
|
@ -127,8 +116,11 @@ ecore_event_current_event_get(void)
|
|||
return ecore_event_message_handler_current_event_get(_event_msg_handler);
|
||||
}
|
||||
|
||||
/* XXX:
|
||||
static Eina_Bool
|
||||
ecore_future_dispatched(void *data EINA_UNUSED, int type EINA_UNUSED, void *event)
|
||||
ecore_future_dispatched(void *data EINA_UNUSED,
|
||||
int type EINA_UNUSED,
|
||||
void *event)
|
||||
{
|
||||
Ecore_Future_Schedule_Entry *entry = event;
|
||||
EINA_SAFETY_ON_NULL_RETURN_VAL(entry, EINA_FALSE);
|
||||
|
@ -139,7 +131,8 @@ ecore_future_dispatched(void *data EINA_UNUSED, int type EINA_UNUSED, void *eve
|
|||
}
|
||||
|
||||
static void
|
||||
ecore_future_free(void *user_data, void *func_data EINA_UNUSED)
|
||||
ecore_future_free(void *user_data,
|
||||
void *func_data EINA_UNUSED)
|
||||
{
|
||||
Ecore_Future_Schedule_Entry *entry = user_data;
|
||||
if (entry->event)
|
||||
|
@ -149,10 +142,35 @@ ecore_future_free(void *user_data, void *func_data EINA_UNUSED)
|
|||
}
|
||||
eina_mempool_free(mp_future_schedule_entry, entry);
|
||||
}
|
||||
*/
|
||||
|
||||
static void
|
||||
_future_dispatch_cb(void *data, const Efl_Event *ev EINA_UNUSED)
|
||||
{
|
||||
Ecore_Future_Schedule_Entry *entry = data;
|
||||
entry->event = NULL;
|
||||
entry->cb(entry->future, entry->value);
|
||||
}
|
||||
|
||||
static void
|
||||
_event_del_cb(void *data, const Efl_Event *ev)
|
||||
{
|
||||
Ecore_Future_Schedule_Entry *entry = data;
|
||||
if ((ev->object == (Eo *) entry->event) && entry->future)
|
||||
{
|
||||
eina_future_cancel(entry->future);
|
||||
eina_value_flush(&entry->value);
|
||||
}
|
||||
eina_mempool_free(mp_future_schedule_entry, entry);
|
||||
}
|
||||
|
||||
static Eina_Future_Schedule_Entry *
|
||||
ecore_future_schedule(Eina_Future_Scheduler *sched, Eina_Future_Scheduler_Cb cb, Eina_Future *future, Eina_Value value)
|
||||
ecore_future_schedule(Eina_Future_Scheduler *sched,
|
||||
Eina_Future_Scheduler_Cb cb,
|
||||
Eina_Future *future,
|
||||
Eina_Value value)
|
||||
{
|
||||
Efl_Loop_Future_Scheduler *loopsched = (Efl_Loop_Future_Scheduler *)sched;
|
||||
Ecore_Future_Schedule_Entry *entry;
|
||||
|
||||
entry = eina_mempool_malloc(mp_future_schedule_entry, sizeof(*entry));
|
||||
|
@ -161,9 +179,19 @@ ecore_future_schedule(Eina_Future_Scheduler *sched, Eina_Future_Scheduler_Cb cb,
|
|||
entry->cb = cb;
|
||||
entry->future = future;
|
||||
entry->value = value;
|
||||
entry->event = ecore_event_add(ECORE_EV_FUTURE_ID, entry, ecore_future_free, entry);
|
||||
entry->event = efl_loop_message_future_handler_message_type_add
|
||||
(loopsched->loop_data->future_message_handler);
|
||||
EINA_SAFETY_ON_NULL_GOTO(entry->event, err);
|
||||
efl_event_callback_add((Eo *) entry->event, EFL_EVENT_DEL, _event_del_cb, entry);
|
||||
efl_loop_message_future_data_set(entry->event, entry);
|
||||
efl_loop_message_handler_message_send
|
||||
(loopsched->loop_data->future_message_handler, entry->event);
|
||||
// XXX:
|
||||
// entry->event = ecore_event_add(ECORE_EV_FUTURE_ID, entry,
|
||||
// ecore_future_free, entry);
|
||||
efl_event_callback_add((Eo *)entry->event, EFL_LOOP_MESSAGE_EVENT_MESSAGE,
|
||||
_future_dispatch_cb, entry);
|
||||
efl_event_callback_add((Eo *)entry->event, EFL_EVENT_DEL,
|
||||
_event_del_cb, entry);
|
||||
return &entry->base;
|
||||
|
||||
err:
|
||||
|
@ -174,12 +202,17 @@ ecore_future_schedule(Eina_Future_Scheduler *sched, Eina_Future_Scheduler_Cb cb,
|
|||
static void
|
||||
ecore_future_recall(Eina_Future_Schedule_Entry *s_entry)
|
||||
{
|
||||
Eo *msg;
|
||||
|
||||
if (shutting_down) return;
|
||||
Ecore_Future_Schedule_Entry *entry = (Ecore_Future_Schedule_Entry *)s_entry;
|
||||
EINA_SAFETY_ON_NULL_RETURN(entry->event);
|
||||
ecore_event_del(entry->event);
|
||||
// XXX:
|
||||
// ecore_event_del(entry->event);
|
||||
msg = entry->event;
|
||||
eina_value_flush(&entry->value);
|
||||
entry->event = NULL;
|
||||
efl_del(msg);
|
||||
}
|
||||
|
||||
static Eina_Future_Scheduler ecore_future_scheduler = {
|
||||
|
@ -238,24 +271,28 @@ _ecore_event_init(void)
|
|||
//////
|
||||
// XXX: ecore future still using legacy...
|
||||
shutting_down = EINA_FALSE;
|
||||
ECORE_EV_FUTURE_ID = ecore_event_type_new();
|
||||
future_handler = ecore_event_handler_add(ECORE_EV_FUTURE_ID, ecore_future_dispatched, NULL);
|
||||
EINA_SAFETY_ON_NULL_GOTO(future_handler, err_handler);
|
||||
// ECORE_EV_FUTURE_ID = ecore_event_type_new();
|
||||
// future_handler = ecore_event_handler_add(ECORE_EV_FUTURE_ID, ecore_future_dispatched, NULL);
|
||||
// EINA_SAFETY_ON_NULL_GOTO(future_handler, err_handler);
|
||||
//FIXME: Is 512 too high?
|
||||
mp_future_schedule_entry = eina_mempool_add(choice, "Ecore_Future_Event",
|
||||
NULL, sizeof(Ecore_Future_Schedule_Entry),
|
||||
512);
|
||||
EINA_SAFETY_ON_NULL_GOTO(mp_future_schedule_entry, err_pool);
|
||||
if (!mp_future_schedule_entry)
|
||||
{
|
||||
mp_future_schedule_entry = eina_mempool_add
|
||||
(choice, "Ecore_Future_Event", NULL,
|
||||
sizeof(Ecore_Future_Schedule_Entry), 512);
|
||||
EINA_SAFETY_ON_NULL_GOTO(mp_future_schedule_entry, err_pool);
|
||||
}
|
||||
//
|
||||
//////
|
||||
|
||||
return EINA_TRUE;
|
||||
|
||||
err_pool:
|
||||
ecore_event_handler_del(future_handler);
|
||||
future_handler = NULL;
|
||||
err_handler:
|
||||
ECORE_EV_FUTURE_ID = -1;
|
||||
// XXX:
|
||||
// ecore_event_handler_del(future_handler);
|
||||
// future_handler = NULL;
|
||||
// err_handler:
|
||||
// ECORE_EV_FUTURE_ID = -1;
|
||||
return EINA_FALSE;
|
||||
}
|
||||
|
||||
|
@ -266,9 +303,9 @@ _ecore_event_shutdown(void)
|
|||
|
||||
//////
|
||||
// XXX: ecore future still using legacy...
|
||||
ecore_event_handler_del(future_handler);
|
||||
future_handler = NULL;
|
||||
ECORE_EV_FUTURE_ID = -1;
|
||||
// ecore_event_handler_del(future_handler);
|
||||
// future_handler = NULL;
|
||||
// ECORE_EV_FUTURE_ID = -1;
|
||||
//
|
||||
//////
|
||||
|
||||
|
|
|
@ -84,6 +84,7 @@ typedef struct _Ecore_Factorized_Idle Ecore_Factorized_Idle;
|
|||
typedef struct _Efl_Loop_Promise_Simple_Data Efl_Loop_Promise_Simple_Data;
|
||||
|
||||
typedef struct _Efl_Loop_Timer_Data Efl_Loop_Timer_Data;
|
||||
typedef struct _Efl_Loop_Future_Scheduler Efl_Loop_Future_Scheduler;
|
||||
typedef struct _Efl_Loop_Data Efl_Loop_Data;
|
||||
|
||||
typedef struct _Message_Handler Message_Handler;
|
||||
|
@ -103,11 +104,22 @@ struct _Message
|
|||
Eina_Bool delete_me;
|
||||
};
|
||||
|
||||
struct _Efl_Loop_Future_Scheduler
|
||||
{
|
||||
Eina_Future_Scheduler eina_future_scheduler;
|
||||
Eo *loop;
|
||||
Efl_Loop_Data *loop_data;
|
||||
};
|
||||
|
||||
struct _Efl_Loop_Data
|
||||
{
|
||||
double loop_time;
|
||||
Eina_Hash *providers;
|
||||
|
||||
Efl_Loop_Future_Scheduler future_scheduler;
|
||||
|
||||
Efl_Loop_Message_Handler *future_message_handler;
|
||||
|
||||
Efl_Loop_Timer *poll_high;
|
||||
Efl_Loop_Timer *poll_medium;
|
||||
Efl_Loop_Timer *poll_low;
|
||||
|
|
|
@ -460,7 +460,10 @@ _efl_loop_timer_efl_object_parent_set(Eo *obj, Efl_Loop_Timer_Data *pd, Efl_Obje
|
|||
_efl_loop_timer_util_loop_clear(pd);
|
||||
|
||||
pd->loop = efl_provider_find(obj, EFL_LOOP_CLASS);
|
||||
pd->loop_data = efl_data_scope_get(pd->loop, EFL_LOOP_CLASS);
|
||||
if (pd->loop)
|
||||
pd->loop_data = efl_data_scope_get(pd->loop, EFL_LOOP_CLASS);
|
||||
else
|
||||
pd->loop_data = NULL;
|
||||
|
||||
if (efl_parent_get(obj) != parent) return;
|
||||
|
||||
|
|
|
@ -307,6 +307,8 @@ _efl_loop_efl_object_constructor(Eo *obj, Efl_Loop_Data *pd)
|
|||
pd->message_handlers = eina_inarray_new(sizeof(Message_Handler), 32);
|
||||
pd->epoll_fd = -1;
|
||||
pd->timer_fd = -1;
|
||||
pd->future_message_handler = efl_loop_message_handler_get
|
||||
(EFL_LOOP_CLASS, obj, EFL_LOOP_MESSAGE_FUTURE_HANDLER_CLASS);
|
||||
return obj;
|
||||
}
|
||||
|
||||
|
@ -315,6 +317,8 @@ _efl_loop_efl_object_destructor(Eo *obj, Efl_Loop_Data *pd)
|
|||
{
|
||||
_ecore_main_content_clear(pd);
|
||||
|
||||
pd->future_message_handler = NULL;
|
||||
|
||||
eina_hash_free(pd->providers);
|
||||
pd->providers = NULL;
|
||||
|
||||
|
@ -325,8 +329,11 @@ _efl_loop_efl_object_destructor(Eo *obj, Efl_Loop_Data *pd)
|
|||
efl_del(pd->poll_high);
|
||||
pd->poll_high = NULL;
|
||||
|
||||
eina_inarray_free(pd->message_handlers);
|
||||
pd->message_handlers = NULL;
|
||||
if (pd->message_handlers)
|
||||
{
|
||||
eina_inarray_free(pd->message_handlers);
|
||||
pd->message_handlers = NULL;
|
||||
}
|
||||
|
||||
efl_destructor(efl_super(obj, EFL_LOOP_CLASS));
|
||||
|
||||
|
@ -439,10 +446,10 @@ ecore_loop_promise_unregister(Efl_Loop *l, Efl_Promise *p)
|
|||
static Eina_Future *
|
||||
_efl_loop_job(Eo *obj, Efl_Loop_Data *pd EINA_UNUSED)
|
||||
{
|
||||
Eina_Future_Scheduler *sched = efl_loop_future_scheduler_get(obj);
|
||||
// NOTE: Eolian should do efl_future_then() to bind future to object.
|
||||
return efl_future_Eina_FutureXXX_then
|
||||
(obj, eina_future_resolved(efl_loop_future_scheduler_get(obj),
|
||||
EINA_VALUE_EMPTY));
|
||||
(obj, eina_future_resolved(sched, EINA_VALUE_EMPTY));
|
||||
}
|
||||
|
||||
EOLIAN static void
|
||||
|
@ -479,6 +486,7 @@ _efl_loop_idle(Eo *obj, Efl_Loop_Data *pd EINA_UNUSED)
|
|||
{
|
||||
Efl_Loop_Promise_Simple_Data *d;
|
||||
Eina_Promise *p;
|
||||
Eina_Future_Scheduler *sched = efl_loop_future_scheduler_get(obj);
|
||||
|
||||
d = efl_loop_promise_simple_data_calloc(1);
|
||||
EINA_SAFETY_ON_NULL_RETURN_VAL(d, NULL);
|
||||
|
@ -486,8 +494,7 @@ _efl_loop_idle(Eo *obj, Efl_Loop_Data *pd EINA_UNUSED)
|
|||
d->idler = ecore_idler_add(_efl_loop_idle_done, d);
|
||||
EINA_SAFETY_ON_NULL_GOTO(d->idler, idler_error);
|
||||
|
||||
p = eina_promise_new(efl_loop_future_scheduler_get(obj),
|
||||
_efl_loop_idle_cancel, d);
|
||||
p = eina_promise_new(sched, _efl_loop_idle_cancel, d);
|
||||
// d is dead if p is NULL
|
||||
EINA_SAFETY_ON_NULL_RETURN_VAL(p, NULL);
|
||||
d->promise = p;
|
||||
|
@ -504,8 +511,11 @@ static void
|
|||
_efl_loop_timeout_cancel(void *data, const Eina_Promise *dead_ptr EINA_UNUSED)
|
||||
{
|
||||
Efl_Loop_Promise_Simple_Data *d = data;
|
||||
efl_del(d->timer);
|
||||
d->timer = NULL;
|
||||
if (d->timer)
|
||||
{
|
||||
efl_del(d->timer);
|
||||
d->timer = NULL;
|
||||
}
|
||||
efl_loop_promise_simple_data_mp_free(d);
|
||||
}
|
||||
|
||||
|
@ -520,11 +530,19 @@ _efl_loop_timeout_done(void *data, const Efl_Event *event)
|
|||
efl_del(event->object);
|
||||
}
|
||||
|
||||
static void
|
||||
_efl_loop_timeout_del(void *data, const Efl_Event *event EINA_UNUSED)
|
||||
{
|
||||
Efl_Loop_Promise_Simple_Data *d = data;
|
||||
d->timer = NULL;
|
||||
}
|
||||
|
||||
static Eina_Future *
|
||||
_efl_loop_timeout(Eo *obj, Efl_Loop_Data *pd EINA_UNUSED, double tim)
|
||||
{
|
||||
Efl_Loop_Promise_Simple_Data *d;
|
||||
Eina_Promise *p;
|
||||
Eina_Future_Scheduler *sched = efl_loop_future_scheduler_get(obj);
|
||||
|
||||
d = efl_loop_promise_simple_data_calloc(1);
|
||||
EINA_SAFETY_ON_NULL_RETURN_VAL(d, NULL);
|
||||
|
@ -533,11 +551,14 @@ _efl_loop_timeout(Eo *obj, Efl_Loop_Data *pd EINA_UNUSED, double tim)
|
|||
efl_loop_timer_interval_set(efl_added, tim),
|
||||
efl_event_callback_add(efl_added,
|
||||
EFL_LOOP_TIMER_EVENT_TICK,
|
||||
_efl_loop_timeout_done, d));
|
||||
_efl_loop_timeout_done, d),
|
||||
efl_event_callback_add(efl_added,
|
||||
EFL_EVENT_DEL,
|
||||
_efl_loop_timeout_del, d)
|
||||
);
|
||||
EINA_SAFETY_ON_NULL_GOTO(d->timer, timer_error);
|
||||
|
||||
p = eina_promise_new(efl_loop_future_scheduler_get(obj),
|
||||
_efl_loop_timeout_cancel, d);
|
||||
p = eina_promise_new(sched, _efl_loop_timeout_cancel, d);
|
||||
// d is dead if p is NULL
|
||||
EINA_SAFETY_ON_NULL_RETURN_VAL(p, NULL);
|
||||
d->promise = p;
|
||||
|
@ -699,7 +720,20 @@ efl_loop_future_scheduler_get(Eo *obj)
|
|||
if (!obj) return NULL;
|
||||
|
||||
if (efl_isa(obj, EFL_LOOP_CLASS))
|
||||
return _ecore_event_future_scheduler_get();
|
||||
{
|
||||
Efl_Loop_Data *pd = efl_data_scope_get(obj, EFL_LOOP_CLASS);
|
||||
|
||||
if (!pd) return NULL;
|
||||
if (!pd->future_scheduler.loop)
|
||||
{
|
||||
Eina_Future_Scheduler *sched =
|
||||
_ecore_event_future_scheduler_get();
|
||||
pd->future_scheduler.eina_future_scheduler = *sched;
|
||||
pd->future_scheduler.loop = obj;
|
||||
pd->future_scheduler.loop_data = pd;
|
||||
}
|
||||
return &(pd->future_scheduler.eina_future_scheduler);
|
||||
}
|
||||
|
||||
return efl_loop_future_scheduler_get(efl_loop_get(obj));
|
||||
}
|
||||
|
|
|
@ -7,6 +7,9 @@ class Efl.Loop.Message (Efl.Object)
|
|||
specific message types.]]
|
||||
methods {
|
||||
}
|
||||
events {
|
||||
message: Efl.Loop.Message; [[The message payload data]]
|
||||
}
|
||||
implements {
|
||||
Efl.Object.constructor;
|
||||
Efl.Object.destructor;
|
||||
|
|
|
@ -0,0 +1,49 @@
|
|||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <Ecore.h>
|
||||
|
||||
#include "ecore_private.h"
|
||||
|
||||
#define MY_CLASS EFL_LOOP_MESSAGE_FUTURE_CLASS
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
typedef struct _Efl_Loop_Message_Future_Data Efl_Loop_Message_Future_Data;
|
||||
|
||||
struct _Efl_Loop_Message_Future_Data
|
||||
{
|
||||
void *data;
|
||||
};
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
EOLIAN static void
|
||||
_efl_loop_message_future_data_set(Eo *obj EINA_UNUSED, Efl_Loop_Message_Future_Data *pd, void *data)
|
||||
{
|
||||
pd->data = data;
|
||||
}
|
||||
|
||||
EOLIAN static void *
|
||||
_efl_loop_message_future_data_get(Eo *obj EINA_UNUSED, Efl_Loop_Message_Future_Data *pd)
|
||||
{
|
||||
return pd->data;
|
||||
}
|
||||
|
||||
EOLIAN static Efl_Object *
|
||||
_efl_loop_message_future_efl_object_constructor(Eo *obj, Efl_Loop_Message_Future_Data *pd EINA_UNUSED)
|
||||
{
|
||||
obj = efl_constructor(efl_super(obj, MY_CLASS));
|
||||
return obj;
|
||||
}
|
||||
|
||||
EOLIAN static void
|
||||
_efl_loop_message_future_efl_object_destructor(Eo *obj, Efl_Loop_Message_Future_Data *pd EINA_UNUSED)
|
||||
{
|
||||
efl_destructor(efl_super(obj, MY_CLASS));
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "efl_loop_message_future.eo.c"
|
|
@ -0,0 +1,21 @@
|
|||
import efl_types;
|
||||
import eina_types;
|
||||
|
||||
class Efl.Loop.Message.Future (Efl.Loop.Message)
|
||||
{
|
||||
[[ Used internally for futures on the loop ]]
|
||||
methods {
|
||||
@property data {
|
||||
[[ ]]
|
||||
set { }
|
||||
get { }
|
||||
values {
|
||||
data: void_ptr; [[ ]]
|
||||
}
|
||||
}
|
||||
}
|
||||
implements {
|
||||
Efl.Object.constructor;
|
||||
Efl.Object.destructor;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <Ecore.h>
|
||||
|
||||
#include "ecore_private.h"
|
||||
|
||||
#define MY_CLASS EFL_LOOP_MESSAGE_FUTURE_HANDLER_CLASS
|
||||
|
||||
typedef struct _Efl_Loop_Message_Future_Handler_Data Efl_Loop_Message_Future_Handler_Data;
|
||||
|
||||
struct _Efl_Loop_Message_Future_Handler_Data
|
||||
{
|
||||
void *data; // dummy;
|
||||
};
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
EOLIAN static Efl_Loop_Message_Future *
|
||||
_efl_loop_message_future_handler_message_type_add(Eo *obj, Efl_Loop_Message_Future_Handler_Data *pd)
|
||||
{
|
||||
// XXX: implemented event obj cache
|
||||
return efl_add(EFL_LOOP_MESSAGE_FUTURE_CLASS, obj);
|
||||
}
|
||||
|
||||
EOLIAN static Efl_Object *
|
||||
_efl_loop_message_future_handler_efl_object_constructor(Eo *obj, Efl_Loop_Message_Future_Handler_Data *pd EINA_UNUSED)
|
||||
{
|
||||
obj = efl_constructor(efl_super(obj, MY_CLASS));
|
||||
return obj;
|
||||
}
|
||||
|
||||
EOLIAN static void
|
||||
_efl_loop_message_future_handler_efl_object_destructor(Eo *obj, Efl_Loop_Message_Future_Handler_Data *pd EINA_UNUSED)
|
||||
{
|
||||
efl_destructor(efl_super(obj, MY_CLASS));
|
||||
}
|
||||
|
||||
EOLIAN static void
|
||||
_efl_loop_message_future_handler_efl_loop_message_handler_message_call(Eo *obj, Efl_Loop_Message_Future_Handler_Data *pd EINA_UNUSED, Efl_Loop_Message *message)
|
||||
{
|
||||
efl_event_callback_call
|
||||
(obj, EFL_LOOP_MESSAGE_FUTURE_HANDLER_EVENT_MESSAGE_FUTURE, message);
|
||||
efl_loop_message_handler_message_call
|
||||
(efl_super(obj, MY_CLASS), message);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "efl_loop_message_future_handler.eo.c"
|
|
@ -0,0 +1,21 @@
|
|||
import efl_types;
|
||||
import eina_types;
|
||||
|
||||
class Efl.Loop.Message.Future.Handler (Efl.Loop.Message.Handler)
|
||||
{
|
||||
[[ Internal use for future on an efl loop - replacing legacy ecore events ]]
|
||||
methods {
|
||||
message_type_add {
|
||||
[[ ]]
|
||||
return: Efl.Loop.Message.Future; [[ ]]
|
||||
}
|
||||
}
|
||||
events {
|
||||
message,future: Efl.Loop.Message.Future; [[ ]]
|
||||
}
|
||||
implements {
|
||||
Efl.Object.constructor;
|
||||
Efl.Object.destructor;
|
||||
Efl.Loop.Message.Handler.message_call; [[ ]]
|
||||
}
|
||||
}
|
|
@ -90,6 +90,8 @@ _efl_loop_message_handler_message_call(Eo *obj, Efl_Loop_Message_Handler_Data *p
|
|||
msg->delete_me = EINA_TRUE;
|
||||
break;
|
||||
}
|
||||
efl_event_callback_call(message, EFL_LOOP_MESSAGE_EVENT_MESSAGE,
|
||||
message);
|
||||
efl_event_callback_call(obj, EFL_LOOP_MESSAGE_HANDLER_EVENT_MESSAGE,
|
||||
message);
|
||||
// XXX: implement message object cache...
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
#endif
|
||||
|
||||
#include "eina_private.h"
|
||||
#include "eina_lock.h"
|
||||
#include "eina_promise.h"
|
||||
#include "eina_mempool.h"
|
||||
#include "eina_promise_private.h"
|
||||
|
@ -117,6 +118,7 @@ struct _Eina_Future {
|
|||
|
||||
static Eina_Mempool *_promise_mp = NULL;
|
||||
static Eina_Mempool *_future_mp = NULL;
|
||||
static Eina_Lock _pending_futures_lock;
|
||||
static Eina_List *_pending_futures = NULL;
|
||||
static int _promise_log_dom = -1;
|
||||
|
||||
|
@ -407,7 +409,9 @@ _eina_future_dispatch(Eina_Future *f, Eina_Value value)
|
|||
static void
|
||||
_scheduled_entry_cb(Eina_Future *f, Eina_Value value)
|
||||
{
|
||||
eina_lock_take(&_pending_futures_lock);
|
||||
_pending_futures = eina_list_remove(_pending_futures, f);
|
||||
eina_lock_release(&_pending_futures_lock);
|
||||
f->scheduled_entry = NULL;
|
||||
_eina_future_dispatch(f, value);
|
||||
}
|
||||
|
@ -436,7 +440,9 @@ _eina_future_cancel(Eina_Future *f, int err)
|
|||
{
|
||||
eina_future_schedule_entry_recall(f->scheduled_entry);
|
||||
f->scheduled_entry = NULL;
|
||||
eina_lock_take(&_pending_futures_lock);
|
||||
_pending_futures = eina_list_remove(_pending_futures, f);
|
||||
eina_lock_release(&_pending_futures_lock);
|
||||
}
|
||||
|
||||
if (f->promise)
|
||||
|
@ -470,7 +476,9 @@ _eina_future_schedule(Eina_Promise *p,
|
|||
f, value);
|
||||
EINA_SAFETY_ON_NULL_GOTO(f->scheduled_entry, err);
|
||||
assert(f->scheduled_entry->scheduler != NULL);
|
||||
eina_lock_take(&_pending_futures_lock);
|
||||
_pending_futures = eina_list_append(_pending_futures, f);
|
||||
eina_lock_release(&_pending_futures_lock);
|
||||
DBG("The promise %p schedule the future %p with cb: %p and data: %p",
|
||||
p, f, f->cb, f->data);
|
||||
return;
|
||||
|
@ -523,6 +531,8 @@ eina_promise_init(void)
|
|||
NULL, sizeof(Eina_Future), 512);
|
||||
EINA_SAFETY_ON_NULL_GOTO(_future_mp, err_future);
|
||||
|
||||
eina_lock_recursive_new(&_pending_futures_lock);
|
||||
|
||||
return EINA_TRUE;
|
||||
|
||||
err_future:
|
||||
|
@ -537,14 +547,17 @@ eina_promise_init(void)
|
|||
EAPI void
|
||||
__eina_promise_cancel_all(void)
|
||||
{
|
||||
eina_lock_take(&_pending_futures_lock);
|
||||
while (_pending_futures)
|
||||
_eina_future_cancel(_pending_futures->data, ECANCELED);
|
||||
eina_lock_release(&_pending_futures_lock);
|
||||
}
|
||||
|
||||
Eina_Bool
|
||||
eina_promise_shutdown(void)
|
||||
{
|
||||
__eina_promise_cancel_all();
|
||||
eina_lock_free(&_pending_futures_lock);
|
||||
eina_mempool_del(_future_mp);
|
||||
eina_mempool_del(_promise_mp);
|
||||
eina_log_domain_unregister(_promise_log_dom);
|
||||
|
|
Loading…
Reference in New Issue