aboutsummaryrefslogtreecommitdiffstats
path: root/legacy/ecore
diff options
context:
space:
mode:
authorCedric BAIL <cedric.bail@free.fr>2011-07-28 13:33:14 +0000
committerCedric BAIL <cedric.bail@free.fr>2011-07-28 13:33:14 +0000
commitb4338b1c7f9e8af20a56c3cecd1793786c78ef34 (patch)
tree4a2bc667e279e6b07c292b0953a9fd2c2ccac744 /legacy/ecore
parentEvas textblock: Fixed a bug with font_weight and font_style. (diff)
downloadefl-b4338b1c7f9e8af20a56c3cecd1793786c78ef34.tar.gz
ecore: add ecore_main_loop_thread_safe_call.
NOTE: that's for you mike. SVN revision: 61857
Diffstat (limited to 'legacy/ecore')
-rw-r--r--legacy/ecore/ChangeLog6
-rw-r--r--legacy/ecore/src/lib/ecore/Ecore.h16
-rw-r--r--legacy/ecore/src/lib/ecore/ecore.c48
3 files changed, 69 insertions, 1 deletions
diff --git a/legacy/ecore/ChangeLog b/legacy/ecore/ChangeLog
index 466e0de851..2b69001e42 100644
--- a/legacy/ecore/ChangeLog
+++ b/legacy/ecore/ChangeLog
@@ -263,9 +263,13 @@
2011-07-22 Mike Blumenkrantz
* Added ecore_con_url_url_get
-
+
2011-07-26 Carsten Haitzler (The Rasterman)
* Fix timer precision handling for grouping timer ticks so
they actually do tick off together
+2011-07-28 Cedric Bail
+
+ * Add ecore_main_loop_thread_safe_call.
+
diff --git a/legacy/ecore/src/lib/ecore/Ecore.h b/legacy/ecore/src/lib/ecore/Ecore.h
index 159aac6160..e57bc17e3f 100644
--- a/legacy/ecore/src/lib/ecore/Ecore.h
+++ b/legacy/ecore/src/lib/ecore/Ecore.h
@@ -737,6 +737,22 @@ extern "C" {
EAPI void *ecore_main_win32_handler_del(Ecore_Win32_Handler *win32_handler);
/**
+ * @brief Call callback in the main loop.
+ *
+ * @param callback The callback to call in the main loop
+ * @param data The data to give to that call back
+ *
+ * For all call that need to happen in the main loop (most EFL functions do),
+ * this helper function provide the infrastructure needed to do it safely
+ * by avoind dead lock, race condition and properly wake up the main loop.
+ *
+ * Remember after that function call, you should never touch again the @p data
+ * in the thread, it is owned by the main loop and you callback should take
+ * care of freeing it if necessary.
+ */
+ EAPI void ecore_main_loop_thread_safe_call(Ecore_Cb callback, void *data);
+
+ /**
* @}
*/
diff --git a/legacy/ecore/src/lib/ecore/ecore.c b/legacy/ecore/src/lib/ecore/ecore.c
index c92c2410a0..b7e0fbd99a 100644
--- a/legacy/ecore/src/lib/ecore/ecore.c
+++ b/legacy/ecore/src/lib/ecore/ecore.c
@@ -53,6 +53,17 @@ static int _ecore_init_count = 0;
int _ecore_log_dom = -1;
int _ecore_fps_debug = 0;
+typedef struct _Ecore_Safe_Call Ecore_Safe_Call;
+struct _Ecore_Safe_Call
+{
+ Ecore_Cb cb;
+ void *data;
+};
+
+static void _thread_callback(void *data, void *buffer, unsigned int nbyte);
+static Ecore_Pipe *_thread_call = NULL;
+static Eina_Lock _thread_safety;
+
/** OpenBSD does not define CODESET
* FIXME ??
*/
@@ -126,6 +137,9 @@ ecore_init(void)
_ecore_job_init();
_ecore_time_init();
+ eina_lock_new(&_thread_safety);
+ _thread_call = ecore_pipe_add(_thread_callback, NULL);
+
#if HAVE_MALLINFO
if (getenv("ECORE_MEM_STAT"))
{
@@ -165,6 +179,9 @@ ecore_shutdown(void)
if (--_ecore_init_count != 0)
return _ecore_init_count;
+ ecore_pipe_del(_thread_call);
+ eina_lock_free(&_thread_safety);
+
if (_ecore_fps_debug) _ecore_fps_debug_shutdown();
_ecore_poller_shutdown();
_ecore_animator_shutdown();
@@ -203,6 +220,22 @@ ecore_shutdown(void)
return _ecore_init_count;
}
+EAPI void
+ecore_main_loop_thread_safe_call(Ecore_Cb callback, void *data)
+{
+ Ecore_Safe_Call *order;
+
+ order = malloc(sizeof (Ecore_Safe_Call));
+ if (!order) return ;
+
+ order->cb = callback;
+ order->data = data;
+
+ eina_lock_take(&_thread_safety);
+ ecore_pipe_write(_thread_call, &order, sizeof (Ecore_Safe_Call*));
+ eina_lock_release(&_thread_safety);
+}
+
/**
* @}
*/
@@ -428,3 +461,18 @@ _ecore_memory_statistic(__UNUSED__ void *data)
}
#endif
+
+static void
+_thread_callback(void *data __UNUSED__, void *buffer, unsigned int nbyte)
+{
+ Ecore_Safe_Call *call = buffer;
+
+ while (nbyte >= sizeof (Ecore_Safe_Call*))
+ {
+ call->cb(call->data);
+ free(call);
+
+ call++;
+ nbyte -= sizeof (Ecore_Safe_Call*);
+ }
+}