mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2025-07-30 05:43:28 +02:00
gsourceclosure: fix idle/timeout/signal closures, add child watch support
And add a test for all source types. https://bugzilla.gnome.org/show_bug.cgi?id=704267
This commit is contained in:
@@ -51,6 +51,31 @@ g_io_condition_get_type (void)
|
||||
return etype;
|
||||
}
|
||||
|
||||
/* We need to hand-write this marshaler, since it doesn't have an
|
||||
* instance object.
|
||||
*/
|
||||
static void
|
||||
source_closure_marshal_BOOLEAN__VOID (GClosure *closure,
|
||||
GValue *return_value,
|
||||
guint n_param_values,
|
||||
const GValue *param_values,
|
||||
gpointer invocation_hint,
|
||||
gpointer marshal_data)
|
||||
{
|
||||
GSourceFunc callback;
|
||||
GCClosure *cc = (GCClosure*) closure;
|
||||
gboolean v_return;
|
||||
|
||||
g_return_if_fail (return_value != NULL);
|
||||
g_return_if_fail (n_param_values == 0);
|
||||
|
||||
callback = (GSourceFunc) (marshal_data ? marshal_data : cc->callback);
|
||||
|
||||
v_return = callback (closure->data);
|
||||
|
||||
g_value_set_boolean (return_value, v_return);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
io_watch_closure_callback (GIOChannel *channel,
|
||||
GIOCondition condition,
|
||||
@@ -79,6 +104,35 @@ io_watch_closure_callback (GIOChannel *channel,
|
||||
return result;
|
||||
}
|
||||
|
||||
static gboolean
|
||||
g_child_watch_closure_callback (GPid pid,
|
||||
gint status,
|
||||
gpointer data)
|
||||
{
|
||||
GClosure *closure = data;
|
||||
|
||||
GValue params[2] = { G_VALUE_INIT, G_VALUE_INIT };
|
||||
GValue result_value = G_VALUE_INIT;
|
||||
gboolean result;
|
||||
|
||||
g_value_init (&result_value, G_TYPE_BOOLEAN);
|
||||
|
||||
g_value_init (¶ms[0], G_TYPE_ULONG);
|
||||
g_value_set_ulong (¶ms[0], pid);
|
||||
|
||||
g_value_init (¶ms[1], G_TYPE_INT);
|
||||
g_value_set_int (¶ms[1], status);
|
||||
|
||||
g_closure_invoke (closure, &result_value, 2, params, NULL);
|
||||
|
||||
result = g_value_get_boolean (&result_value);
|
||||
g_value_unset (&result_value);
|
||||
g_value_unset (¶ms[0]);
|
||||
g_value_unset (¶ms[1]);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
#ifdef G_OS_UNIX
|
||||
static gboolean
|
||||
g_unix_fd_source_closure_callback (int fd,
|
||||
@@ -138,7 +192,9 @@ closure_callback_get (gpointer cb_data,
|
||||
if (!closure_callback)
|
||||
{
|
||||
if (source->source_funcs == &g_io_watch_funcs)
|
||||
closure_callback = (GSourceFunc)io_watch_closure_callback;
|
||||
closure_callback = (GSourceFunc)io_watch_closure_callback;
|
||||
else if (source->source_funcs == &g_child_watch_funcs)
|
||||
closure_callback = (GSourceFunc)g_child_watch_closure_callback;
|
||||
#ifdef G_OS_UNIX
|
||||
else if (source->source_funcs == &g_unix_fd_source_funcs)
|
||||
closure_callback = (GSourceFunc)g_unix_fd_source_closure_callback;
|
||||
@@ -147,8 +203,8 @@ closure_callback_get (gpointer cb_data,
|
||||
#ifdef G_OS_UNIX
|
||||
source->source_funcs == &g_unix_signal_funcs ||
|
||||
#endif
|
||||
source->source_funcs == &g_idle_funcs)
|
||||
closure_callback = source_closure_callback;
|
||||
source->source_funcs == &g_idle_funcs)
|
||||
closure_callback = source_closure_callback;
|
||||
}
|
||||
|
||||
*func = closure_callback;
|
||||
@@ -191,6 +247,7 @@ g_source_set_closure (GSource *source,
|
||||
source->source_funcs != &g_unix_fd_source_funcs &&
|
||||
source->source_funcs != &g_unix_signal_funcs &&
|
||||
#endif
|
||||
source->source_funcs != &g_child_watch_funcs &&
|
||||
source->source_funcs != &g_io_watch_funcs &&
|
||||
source->source_funcs != &g_timeout_funcs &&
|
||||
source->source_funcs != &g_idle_funcs)
|
||||
@@ -210,6 +267,12 @@ g_source_set_closure (GSource *source,
|
||||
GClosureMarshal marshal = (GClosureMarshal)source->source_funcs->closure_marshal;
|
||||
if (marshal)
|
||||
g_closure_set_marshal (closure, marshal);
|
||||
else if (source->source_funcs == &g_idle_funcs ||
|
||||
#ifdef G_OS_UNIX
|
||||
source->source_funcs == &g_unix_signal_funcs ||
|
||||
#endif
|
||||
source->source_funcs == &g_timeout_funcs)
|
||||
g_closure_set_marshal (closure, source_closure_marshal_BOOLEAN__VOID);
|
||||
else
|
||||
g_closure_set_marshal (closure, g_cclosure_marshal_generic);
|
||||
}
|
||||
|
Reference in New Issue
Block a user