forked from enlightenment/efl
ecore: move Ecore_Idler to legacy and rely on Eo event restart capability.
This commit is contained in:
parent
559d4e8b68
commit
3ff21c021d
|
@ -6,7 +6,6 @@ ecore_eolian_files_legacy = \
|
|||
lib/ecore/ecore_poller.eo \
|
||||
lib/ecore/ecore_job.eo \
|
||||
lib/ecore/ecore_exe.eo \
|
||||
lib/ecore/ecore_idler.eo \
|
||||
lib/ecore/ecore_idle_enterer.eo \
|
||||
lib/ecore/ecore_idle_exiter.eo \
|
||||
lib/ecore/ecore_animator.eo
|
||||
|
|
|
@ -3033,9 +3033,7 @@ EAPI char *ecore_timer_dump(void);
|
|||
/*
|
||||
* @since 1.8
|
||||
*/
|
||||
typedef Eo Ecore_Idler; /**< A handle for idlers */
|
||||
|
||||
#define _ECORE_IDLER_EO_CLASS_TYPE
|
||||
typedef struct _Ecore_Idler Ecore_Idler; /**< A handle for idlers */
|
||||
|
||||
/*
|
||||
* @since 1.8
|
||||
|
|
|
@ -47,7 +47,6 @@ extern "C" {
|
|||
* @{
|
||||
*/
|
||||
|
||||
#include "ecore_idler.eo.h"
|
||||
#include "ecore_idle_exiter.eo.h"
|
||||
#include "ecore_idle_enterer.eo.h"
|
||||
|
||||
|
|
|
@ -246,6 +246,7 @@ EAPI void ecore_timer_thaw(Ecore_Timer *timer);
|
|||
*
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
* Add an idler handler.
|
||||
* @param func The function to call when idling.
|
||||
|
@ -321,8 +322,6 @@ EAPI Ecore_Idle_Exiter *ecore_idle_exiter_add(Ecore_Task_Cb func, const void *da
|
|||
*/
|
||||
EAPI void *ecore_idle_exiter_del(Ecore_Idle_Exiter *idle_exiter);
|
||||
|
||||
#include "ecore_idler.eo.legacy.h"
|
||||
|
||||
/**
|
||||
* @}
|
||||
*/
|
||||
|
|
|
@ -402,7 +402,6 @@ ecore_shutdown(void)
|
|||
#endif
|
||||
_ecore_idle_enterer_shutdown();
|
||||
_ecore_idle_exiter_shutdown();
|
||||
_ecore_idler_shutdown();
|
||||
_ecore_timer_shutdown();
|
||||
_ecore_event_shutdown();
|
||||
_ecore_main_shutdown();
|
||||
|
|
|
@ -9,55 +9,77 @@
|
|||
#include "Ecore.h"
|
||||
#include "ecore_private.h"
|
||||
|
||||
#define MY_CLASS ECORE_IDLER_CLASS
|
||||
|
||||
#define MY_CLASS_NAME "Ecore_Idler"
|
||||
|
||||
struct _Ecore_Idler_Data
|
||||
struct _Ecore_Idler
|
||||
{
|
||||
EINA_INLIST;
|
||||
Ecore_Idler *obj;
|
||||
Ecore_Task_Cb func;
|
||||
void *data;
|
||||
int references;
|
||||
Eina_Bool delete_me : 1;
|
||||
};
|
||||
|
||||
typedef struct _Ecore_Idler_Data Ecore_Idler_Data;
|
||||
static Ecore_Idler_Data *idlers = NULL;
|
||||
static Ecore_Idler_Data *idler_current = NULL;
|
||||
static int idlers_delete_me = 0;
|
||||
static void *_ecore_idler_del(Ecore_Idler *idler);
|
||||
|
||||
static Eina_Bool
|
||||
_ecore_idler_event_del(void *data, const Eo_Event *event EINA_UNUSED)
|
||||
{
|
||||
_ecore_idler_del(data);
|
||||
|
||||
return EO_CALLBACK_CONTINUE;
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
_ecore_idler_process(void *data, const Eo_Event *event EINA_UNUSED)
|
||||
{
|
||||
Ecore_Idler *idler = data;
|
||||
|
||||
if (!_ecore_call_task_cb(idler->func, idler->data))
|
||||
_ecore_idler_del(idler);
|
||||
|
||||
return EO_CALLBACK_CONTINUE;
|
||||
}
|
||||
|
||||
EO_CALLBACKS_ARRAY_DEFINE(ecore_idler_callbacks,
|
||||
{ ECORE_MAINLOOP_EVENT_IDLE, _ecore_idler_process },
|
||||
{ EO_BASE_EVENT_DEL, _ecore_idler_event_del });
|
||||
|
||||
static void *
|
||||
_ecore_idler_del(Ecore_Idler *idler);
|
||||
_ecore_idler_del(Ecore_Idler *idler)
|
||||
{
|
||||
void *data;
|
||||
|
||||
if (!idler) return NULL;
|
||||
|
||||
eo_event_callback_array_del(_mainloop_singleton, ecore_idler_callbacks(), idler);
|
||||
|
||||
data = idler->data;
|
||||
free(idler);
|
||||
return data;
|
||||
}
|
||||
|
||||
EAPI Ecore_Idler *
|
||||
ecore_idler_add(Ecore_Task_Cb func,
|
||||
const void *data)
|
||||
{
|
||||
return eo_add(MY_CLASS, _ecore_parent, ecore_idler_constructor(eo_self, func, data));
|
||||
}
|
||||
Ecore_Idler *ret;
|
||||
|
||||
EOLIAN static void
|
||||
_ecore_idler_constructor(Eo *obj, Ecore_Idler_Data *ie, Ecore_Task_Cb func, const void *data)
|
||||
{
|
||||
if (EINA_UNLIKELY(!eina_main_loop_is()))
|
||||
{
|
||||
EINA_MAIN_LOOP_CHECK_RETURN;
|
||||
}
|
||||
|
||||
ie->obj = obj;
|
||||
eo_manual_free_set(obj, EINA_TRUE);
|
||||
if (EINA_UNLIKELY(!eina_main_loop_is()))
|
||||
{
|
||||
EINA_MAIN_LOOP_CHECK_RETURN;
|
||||
}
|
||||
|
||||
if (!func)
|
||||
{
|
||||
ERR("callback function must be set up for an object of class: '%s'", MY_CLASS_NAME);
|
||||
return;
|
||||
ERR("callback function must be set up for an object of Ecore_Idler.");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ie->func = func;
|
||||
ie->data = (void *)data;
|
||||
idlers = (Ecore_Idler_Data *)eina_inlist_append(EINA_INLIST_GET(idlers), EINA_INLIST_GET(ie));
|
||||
ret = malloc(sizeof (Ecore_Idler));
|
||||
if (!ret) return NULL;
|
||||
|
||||
ret->func = func;
|
||||
ret->data = (void*) data;
|
||||
|
||||
eo_event_callback_array_add(_mainloop_singleton, ecore_idler_callbacks(), ret);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
EAPI void *
|
||||
|
@ -69,123 +91,16 @@ ecore_idler_del(Ecore_Idler *idler)
|
|||
return _ecore_idler_del(idler);
|
||||
}
|
||||
|
||||
static void *
|
||||
_ecore_idler_del(Ecore_Idler *obj)
|
||||
{
|
||||
Ecore_Idler_Data *idler = eo_data_scope_get(obj, MY_CLASS);
|
||||
if (!idler) return NULL;
|
||||
EINA_SAFETY_ON_TRUE_RETURN_VAL(idler->delete_me, NULL);
|
||||
idler->delete_me = 1;
|
||||
idlers_delete_me = 1;
|
||||
return idler->data;
|
||||
}
|
||||
|
||||
EOLIAN static void
|
||||
_ecore_idler_eo_base_destructor(Eo *obj, Ecore_Idler_Data *idler)
|
||||
{
|
||||
idler->delete_me = 1;
|
||||
idlers_delete_me = 1;
|
||||
|
||||
eo_destructor(eo_super(obj, MY_CLASS));
|
||||
}
|
||||
|
||||
EOLIAN static Eo *
|
||||
_ecore_idler_eo_base_finalize(Eo *obj, Ecore_Idler_Data *idler)
|
||||
{
|
||||
if (!idler->func)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return eo_finalize(eo_super(obj, MY_CLASS));
|
||||
}
|
||||
|
||||
void
|
||||
_ecore_idler_shutdown(void)
|
||||
_ecore_idler_all_call(Eo *loop)
|
||||
{
|
||||
Ecore_Idler_Data *ie;
|
||||
while ((ie = idlers))
|
||||
{
|
||||
idlers = (Ecore_Idler_Data *)eina_inlist_remove(EINA_INLIST_GET(idlers), EINA_INLIST_GET(idlers));
|
||||
|
||||
eo_parent_set(ie->obj, NULL);
|
||||
if (eo_destructed_is(ie->obj))
|
||||
eo_manual_free(ie->obj);
|
||||
else
|
||||
eo_manual_free_set(ie->obj, EINA_FALSE);
|
||||
}
|
||||
idlers_delete_me = 0;
|
||||
idler_current = NULL;
|
||||
eo_event_callback_call(loop, ECORE_MAINLOOP_EVENT_IDLE, NULL);
|
||||
}
|
||||
|
||||
int
|
||||
_ecore_idler_all_call(void)
|
||||
_ecore_idler_exist(Eo *loop)
|
||||
{
|
||||
if (!idler_current)
|
||||
{
|
||||
/* regular main loop, start from head */
|
||||
idler_current = idlers;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* recursive main loop, continue from where we were */
|
||||
idler_current = (Ecore_Idler_Data *)EINA_INLIST_GET(idler_current)->next;
|
||||
}
|
||||
Ecore_Mainloop_Data *dt = eo_data_scope_get(loop, ECORE_MAINLOOP_CLASS);
|
||||
|
||||
while (idler_current)
|
||||
{
|
||||
Ecore_Idler_Data *ie = (Ecore_Idler_Data *)idler_current;
|
||||
if (!ie->delete_me)
|
||||
{
|
||||
ie->references++;
|
||||
eina_evlog("+idler", ie, 0.0, NULL);
|
||||
if (!_ecore_call_task_cb(ie->func, ie->data))
|
||||
{
|
||||
if (!ie->delete_me) _ecore_idler_del(ie->obj);
|
||||
}
|
||||
eina_evlog("-idler", ie, 0.0, NULL);
|
||||
ie->references--;
|
||||
}
|
||||
if (idler_current) /* may have changed in recursive main loops */
|
||||
idler_current = (Ecore_Idler_Data *)EINA_INLIST_GET(idler_current)->next;
|
||||
}
|
||||
if (idlers_delete_me)
|
||||
{
|
||||
Ecore_Idler_Data *l;
|
||||
int deleted_idlers_in_use = 0;
|
||||
for (l = idlers; l; )
|
||||
{
|
||||
Ecore_Idler_Data *ie = l;
|
||||
l = (Ecore_Idler_Data *)EINA_INLIST_GET(l)->next;
|
||||
if (ie->delete_me)
|
||||
{
|
||||
if (ie->references)
|
||||
{
|
||||
deleted_idlers_in_use++;
|
||||
continue;
|
||||
}
|
||||
|
||||
idlers = (Ecore_Idler_Data *)eina_inlist_remove(EINA_INLIST_GET(idlers), EINA_INLIST_GET(ie));
|
||||
|
||||
eo_parent_set(ie->obj, NULL);
|
||||
if (eo_destructed_is(ie->obj))
|
||||
eo_manual_free(ie->obj);
|
||||
else
|
||||
eo_manual_free_set(ie->obj, EINA_FALSE);
|
||||
}
|
||||
}
|
||||
if (!deleted_idlers_in_use)
|
||||
idlers_delete_me = 0;
|
||||
}
|
||||
if (idlers) return 1;
|
||||
return 0;
|
||||
return dt->idlers;
|
||||
}
|
||||
|
||||
int
|
||||
_ecore_idler_exist(void)
|
||||
{
|
||||
if (idlers) return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
#include "ecore_idler.eo.c"
|
||||
|
|
|
@ -1,28 +0,0 @@
|
|||
import ecore_types;
|
||||
|
||||
class Ecore.Idler (Eo.Base)
|
||||
{
|
||||
[[Setup callbacks to be called when the program is in idle state.
|
||||
|
||||
Once the mainloop has called all enterer handlers it calls the registered
|
||||
idler callbacks.
|
||||
]]
|
||||
eo_prefix: ecore_idler;
|
||||
methods {
|
||||
constructor {
|
||||
[[Constructor.]]
|
||||
legacy: null;
|
||||
params {
|
||||
@in func: Ecore_Task_Cb; [[Idler callback function.]]
|
||||
@in data: const(void)*; [[Private data passed to callback functions.]]
|
||||
}
|
||||
}
|
||||
}
|
||||
implements {
|
||||
Eo.Base.destructor;
|
||||
Eo.Base.finalize;
|
||||
}
|
||||
constructors {
|
||||
.constructor;
|
||||
}
|
||||
}
|
|
@ -722,7 +722,7 @@ _ecore_main_gsource_prepare(GSource *source EINA_UNUSED,
|
|||
if (g_main_loop_is_running(ecore_main_loop))
|
||||
{
|
||||
/* only set idling state in dispatch */
|
||||
if (ecore_idling && !_ecore_idler_exist() && !_ecore_event_exist())
|
||||
if (ecore_idling && !_ecore_idler_exist(_mainloop_singleton) && !_ecore_event_exist())
|
||||
{
|
||||
if (_ecore_timers_exists())
|
||||
{
|
||||
|
@ -791,7 +791,7 @@ _ecore_main_gsource_check(GSource *source EINA_UNUSED)
|
|||
in_main_loop++;
|
||||
|
||||
/* check if old timers expired */
|
||||
if (ecore_idling && !_ecore_idler_exist() && !_ecore_event_exist())
|
||||
if (ecore_idling && !_ecore_idler_exist(_mainloop_singleton) && !_ecore_event_exist())
|
||||
{
|
||||
if (timer_fd >= 0)
|
||||
{
|
||||
|
@ -846,7 +846,7 @@ _ecore_main_gsource_dispatch(GSource *source EINA_UNUSED,
|
|||
|
||||
events_ready = _ecore_event_exist();
|
||||
timers_ready = _ecore_timers_exists() && (0.0 == next_time);
|
||||
idlers_ready = _ecore_idler_exist();
|
||||
idlers_ready = _ecore_idler_exist(_mainloop_singleton);
|
||||
|
||||
in_main_loop++;
|
||||
DBG("enter idling=%d fds=%d events=%d timers=%d (next=%.2f) idlers=%d",
|
||||
|
@ -866,7 +866,7 @@ _ecore_main_gsource_dispatch(GSource *source EINA_UNUSED,
|
|||
|
||||
if (ecore_idling)
|
||||
{
|
||||
_ecore_idler_all_call();
|
||||
_ecore_idler_all_call(_mainloop_singleton);
|
||||
|
||||
events_ready = _ecore_event_exist();
|
||||
|
||||
|
@ -2091,9 +2091,9 @@ _ecore_main_loop_uv_prepare(uv_prepare_t* handle EINA_UNUSED)
|
|||
double t = -1;
|
||||
if(_ecore_main_uv_idling)
|
||||
{
|
||||
_ecore_idler_all_call();
|
||||
_ecore_idler_all_call(_mainloop_singleton);
|
||||
DBG("called idles");
|
||||
if(_ecore_idler_exist() || _ecore_event_exist())
|
||||
if(_ecore_idler_exist(_mainloop_singleton) || _ecore_event_exist())
|
||||
t = 0.0;
|
||||
}
|
||||
|
||||
|
@ -2159,8 +2159,10 @@ _ecore_main_loop_spin_core(void)
|
|||
{
|
||||
/* as we are spinning we need to update loop time per spin */
|
||||
_ecore_time_loop_time = ecore_time_get();
|
||||
/* call all idlers, which returns false if no more idelrs exist */
|
||||
if (!_ecore_idler_all_call()) return SPIN_RESTART;
|
||||
/* call all idlers */
|
||||
_ecore_idler_all_call(_mainloop_singleton);
|
||||
/* which returns false if no more idelrs exist */
|
||||
if (!_ecore_idler_exist(_mainloop_singleton)) return SPIN_RESTART;
|
||||
/* sneaky - drop through or if checks - the first one to succeed
|
||||
* drops through and returns "continue" so further ones dont run */
|
||||
if ((_ecore_main_select(0.0) > 0) || (_ecore_event_exist()) ||
|
||||
|
@ -2305,7 +2307,7 @@ start_loop: /*-*************************************************************/
|
|||
/* init flags */
|
||||
next_time = _ecore_timer_next_get();
|
||||
/* no idlers */
|
||||
if (!_ecore_idler_exist())
|
||||
if (!_ecore_idler_exist(_mainloop_singleton))
|
||||
{
|
||||
/* sleep until timeout or forever (-1.0) waiting for on fds */
|
||||
_ecore_main_select(next_time);
|
||||
|
@ -2764,4 +2766,53 @@ _ecore_mainloop_animator_ticked(Eo *obj EINA_UNUSED, Ecore_Mainloop_Data *pd EIN
|
|||
return ecore_main_loop_animator_ticked_get();
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
_check_event_catcher_add(void *data, const Eo_Event *event)
|
||||
{
|
||||
const Eo_Callback_Array_Item *array = event->info;
|
||||
Ecore_Mainloop_Data *pd = data;
|
||||
int i;
|
||||
|
||||
for (i = 0; array[i].desc != NULL; i++)
|
||||
{
|
||||
if (array[i].desc == ECORE_MAINLOOP_EVENT_IDLE)
|
||||
{
|
||||
++pd->idlers;
|
||||
}
|
||||
}
|
||||
|
||||
return EO_CALLBACK_CONTINUE;
|
||||
}
|
||||
|
||||
static Eina_Bool
|
||||
_check_event_catcher_del(void *data, const Eo_Event *event)
|
||||
{
|
||||
const Eo_Callback_Array_Item *array = event->info;
|
||||
Ecore_Mainloop_Data *pd = data;
|
||||
int i;
|
||||
|
||||
for (i = 0; array[i].desc != NULL; i++)
|
||||
{
|
||||
if (array[i].desc == ECORE_MAINLOOP_EVENT_IDLE)
|
||||
{
|
||||
--pd->idlers;
|
||||
}
|
||||
}
|
||||
|
||||
return EO_CALLBACK_CONTINUE;
|
||||
}
|
||||
|
||||
EO_CALLBACKS_ARRAY_DEFINE(event_catcher_watch,
|
||||
{ EO_BASE_EVENT_CALLBACK_ADD, _check_event_catcher_add },
|
||||
{ EO_BASE_EVENT_CALLBACK_DEL, _check_event_catcher_del });
|
||||
|
||||
EOLIAN static Eo_Base *
|
||||
_ecore_mainloop_eo_base_constructor(Eo *obj, Ecore_Mainloop_Data *pd)
|
||||
{
|
||||
eo_constructor(eo_super(obj, ECORE_MAINLOOP_CLASS));
|
||||
eo_event_callback_array_add(obj, event_catcher_watch(), pd);
|
||||
|
||||
return obj;
|
||||
}
|
||||
|
||||
#include "ecore_mainloop.eo.c"
|
||||
|
|
|
@ -52,7 +52,10 @@ class Ecore_Mainloop (Eo.Base)
|
|||
events {
|
||||
idle,enter @restart; [[Event occurs once the main loop enters the idle state.]]
|
||||
idle,exit @restart; [[Event occurs once the main loop exits the idle state.]]
|
||||
idle @restart; /* FIXME: We need to make sure we can get it work. */
|
||||
idle @restart; [[Event occurs once the main loop is idler. Be carefull, this will spin your CPU high if you keep listening on this event.]]
|
||||
/* TODO: All of the legacy ecore events. (Ecore.h header) */
|
||||
}
|
||||
implements {
|
||||
Eo.Base.constructor;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -85,6 +85,12 @@ extern int _ecore_log_dom;
|
|||
# define CLAMP(x, min, max) (((x) > (max)) ? (max) : (((x) < (min)) ? (min) : (x)))
|
||||
#endif
|
||||
|
||||
typedef struct _Ecore_Mainloop_Data Ecore_Mainloop_Data;
|
||||
struct _Ecore_Mainloop_Data
|
||||
{
|
||||
int idlers;
|
||||
};
|
||||
|
||||
#define EVAS_FRAME_QUEUING 1 /* for test */
|
||||
|
||||
#define READBUFSIZ 65536
|
||||
|
@ -165,9 +171,8 @@ int _ecore_timers_exists(void);
|
|||
|
||||
int _ecore_timer_expired_call(double when);
|
||||
|
||||
void _ecore_idler_shutdown(void);
|
||||
int _ecore_idler_all_call(void);
|
||||
int _ecore_idler_exist(void);
|
||||
void _ecore_idler_all_call(Eo *loop);
|
||||
int _ecore_idler_exist(Eo *loop);
|
||||
|
||||
void _ecore_idle_enterer_shutdown(void);
|
||||
void _ecore_idle_enterer_call(void);
|
||||
|
|
Loading…
Reference in New Issue