[systemd-devel] [PATCH 3/4] gdbus: Integrate kdbus into GDBus core

Karol Lewandowski k.lewandowsk at samsung.com
Thu Nov 21 03:33:51 PST 2013


This commit hooks kdbus into GDBus and provides
"--enable-kdbus-transport" configure switch.
---
 configure.ac          |  10 +++
 gio/Makefile.am       |   4 +
 gio/gdbusaddress.c    |  80 +++++++++++++++----
 gio/gdbusconnection.c |  20 ++++-
 gio/gdbusprivate.c    | 211 ++++++++++++++++++++++++++++++++++++++++++++++----
 gio/gdbusprivate.h    |   8 +-
 gio/giotypes.h        |  33 ++++++++
 7 files changed, 334 insertions(+), 32 deletions(-)

diff --git a/configure.ac b/configure.ac
index deacdc1..413c9f2 100644
--- a/configure.ac
+++ b/configure.ac
@@ -242,6 +242,10 @@ AC_ARG_ENABLE(gc_friendly,
               [AS_HELP_STRING([--enable-gc-friendly],
                               [turn on garbage collector friendliness [default=no]])],,
               [enable_gc_friendly=no])
+AC_ARG_ENABLE(kdbus_transport,
+              [AS_HELP_STRING([--enable-kdbus-transport],
+                             [enable kdbus transport [default=no]])],,
+              [enable_kdbus_transport=no])
 AC_ARG_ENABLE(mem_pools,
               [AS_HELP_STRING([--disable-mem-pools],
 			      [disable all glib memory pools])],,
@@ -259,6 +263,12 @@ AS_IF([test "x$enable_gc_friendly" = "xyes"], [
   AC_MSG_RESULT([yes])
 ], [ AC_MSG_RESULT([no]) ])
 
+AC_MSG_CHECKING([kdbus transport])
+AS_IF([test "x$enable_kdbus_transport" = "xyes"], [
+  AC_DEFINE(KDBUS_TRANSPORT, 1, [Define if kdbus transport is enabled])
+  AC_MSG_RESULT([yes])
+], [ AC_MSG_RESULT([no]) ])
+
 AC_MSG_CHECKING([whether to disable memory pools])
 AS_IF([test "x$disable_mem_pools" = "xno"], [
   AC_MSG_RESULT([no])
diff --git a/gio/Makefile.am b/gio/Makefile.am
index 5b6cda1..c060ef2 100644
--- a/gio/Makefile.am
+++ b/gio/Makefile.am
@@ -394,6 +394,8 @@ libgio_2_0_la_SOURCES =		\
 	giostream.c		\
 	gioprivate.h		\
 	giowin32-priv.h 	\
+	gkdbus.c                \
+	gkdbusconnection.c	\
 	gloadableicon.c 	\
 	gmount.c 		\
 	gmemoryinputstream.c 	\
@@ -569,6 +571,8 @@ gio_headers =			\
 	giomodule.h 		\
 	gioscheduler.h 		\
 	giostream.h		\
+	gkdbus.h                \
+	gkdbusconnection.h	\
 	gloadableicon.h 	\
 	gmount.h 		\
 	gmemoryinputstream.h 	\
diff --git a/gio/gdbusaddress.c b/gio/gdbusaddress.c
index b5143cf..bed0bbe 100644
--- a/gio/gdbusaddress.c
+++ b/gio/gdbusaddress.c
@@ -1,6 +1,7 @@
 /* GDBus - GLib D-Bus Library
  *
  * Copyright (C) 2008-2010 Red Hat, Inc.
+ * Copyright (C) 2013 Samsung Electronics
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Lesser General Public
@@ -17,7 +18,9 @@
  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
  * Boston, MA 02111-1307, USA.
  *
- * Author: David Zeuthen <davidz at redhat.com>
+ * Author: David Zeuthen        <davidz at redhat.com>
+ * Author: Lukasz Skalski       <l.skalski at partner.samsung.com>
+ * Author: Michal Eljasiewicz   <m.eljasiewic at samsung.com>
  */
 
 #include "config.h"
@@ -44,6 +47,7 @@
 
 #ifdef G_OS_UNIX
 #include <gio/gunixsocketaddress.h>
+#include <gio/gkdbusconnection.h>
 #endif
 
 #ifdef G_OS_WIN32
@@ -360,6 +364,18 @@ is_valid_tcp (const gchar  *address_entry,
   return ret;
 }
 
+static int
+g_dbus_is_supported_address_kdbus (const gchar  *transport_name)
+{
+  int supported = 0;
+
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  supported = (g_strcmp0 (transport_name, "kdbus") == 0) || (g_strcmp0 (transport_name, "kernel") == 0);
+#endif
+
+  return supported;
+}
+
 /**
  * g_dbus_is_supported_address:
  * @string: A string.
@@ -401,7 +417,8 @@ g_dbus_is_supported_address (const gchar  *string,
         goto out;
 
       supported = FALSE;
-      if (g_strcmp0 (transport_name, "unix") == 0)
+      if ((g_strcmp0 (transport_name, "unix") == 0)
+          || g_dbus_is_supported_address_kdbus (transport_name))
         supported = is_valid_unix (a[n], key_value_pairs, error);
       else if (g_strcmp0 (transport_name, "tcp") == 0)
         supported = is_valid_tcp (a[n], key_value_pairs, error);
@@ -553,7 +570,8 @@ g_dbus_address_connect (const gchar   *address_entry,
     {
     }
 #ifdef G_OS_UNIX
-  else if (g_strcmp0 (transport_name, "unix") == 0)
+  if ((g_strcmp0 (transport_name, "unix") == 0)
+      || g_dbus_is_supported_address_kdbus (transport_name))
     {
       const gchar *path;
       const gchar *abstract;
@@ -664,21 +682,49 @@ g_dbus_address_connect (const gchar   *address_entry,
 
   if (connectable != NULL)
     {
-      GSocketClient *client;
-      GSocketConnection *connection;
-
-      g_assert (ret == NULL);
-      client = g_socket_client_new ();
-      connection = g_socket_client_connect (client,
-                                            connectable,
-                                            cancellable,
-                                            error);
-      g_object_unref (connectable);
-      g_object_unref (client);
-      if (connection == NULL)
-        goto out;
 
-      ret = G_IO_STREAM (connection);
+      if (FALSE)
+        {
+        }
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+      else if (g_dbus_is_supported_address_kdbus (transport_name))
+        {
+          GKdbusConnection *connection;
+
+          const gchar *path;
+          path = g_hash_table_lookup (key_value_pairs, "path");
+
+          g_assert (ret == NULL);
+          connection = g_kdbus_connection_new ();
+          g_kdbus_connection_connect (connection,
+                                      path,
+                                      cancellable,
+                                      error);
+          g_object_unref (connectable);
+          if (connection == NULL)
+            goto out;
+
+          ret = G_IO_STREAM (connection);
+        }
+#endif
+      else
+        {
+          GSocketClient *client;
+          GSocketConnection *connection;
+
+          g_assert (ret == NULL);
+          client = g_socket_client_new ();
+          connection = g_socket_client_connect (client,
+                                                connectable,
+                                                cancellable,
+                                                error);
+          g_object_unref (connectable);
+          g_object_unref (client);
+          if (connection == NULL)
+            goto out;
+
+          ret = G_IO_STREAM (connection);
+        }
 
       if (nonce_file != NULL)
         {
diff --git a/gio/gdbusconnection.c b/gio/gdbusconnection.c
index 8a0748d..790a21c 100644
--- a/gio/gdbusconnection.c
+++ b/gio/gdbusconnection.c
@@ -1,6 +1,7 @@
 /* GDBus - GLib D-Bus Library
  *
  * Copyright (C) 2008-2010 Red Hat, Inc.
+ * Copyright (C) 2013 Samsung Electronics
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Lesser General Public
@@ -17,7 +18,9 @@
  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
  * Boston, MA 02111-1307, USA.
  *
- * Author: David Zeuthen <davidz at redhat.com>
+ * Author: David Zeuthen        <davidz at redhat.com>
+ * Author: Lukasz Skalski       <l.skalski at partner.samsung.com>
+ * Author: Michal Eljasiewicz   <m.eljasiewic at samsung.com>
  */
 
 /*
@@ -128,6 +131,7 @@
 #include "gsimpleasyncresult.h"
 
 #ifdef G_OS_UNIX
+#include "gkdbusconnection.h"
 #include "gunixconnection.h"
 #include "gunixfdmessage.h"
 #endif
@@ -1659,6 +1663,14 @@ g_dbus_connection_send_message_unlocked (GDBusConnection   *connection,
                        error))
     goto out;
 
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  if (G_IS_KDBUS_CONNECTION (connection->stream))
+    {
+      if ((connection->bus_unique_name) != NULL)
+        g_dbus_message_set_sender(message, connection->bus_unique_name);
+    }
+#endif
+
   blob = g_dbus_message_to_blob (message,
                                  &blob_size,
                                  connection->capabilities,
@@ -2591,6 +2603,10 @@ initable_init (GInitable     *initable,
       g_assert_not_reached ();
     }
 
+  /* TODO: [KDBUS] Our kdbus daemon doesn't support connection authentication */
+  if (G_IS_KDBUS_CONNECTION (connection->stream))
+    goto authenticated;
+
   /* Authenticate the connection */
   if (connection->flags & G_DBUS_CONNECTION_FLAGS_AUTHENTICATION_SERVER)
     {
@@ -2629,6 +2645,8 @@ initable_init (GInitable     *initable,
       connection->authentication_observer = NULL;
     }
 
+authenticated:
+
   //g_output_stream_flush (G_SOCKET_CONNECTION (connection->stream)
 
   //g_debug ("haz unix fd passing powers: %d", connection->capabilities & G_DBUS_CAPABILITY_FLAGS_UNIX_FD_PASSING);
diff --git a/gio/gdbusprivate.c b/gio/gdbusprivate.c
index 785a0c0..9d76708 100644
--- a/gio/gdbusprivate.c
+++ b/gio/gdbusprivate.c
@@ -1,6 +1,7 @@
 /* GDBus - GLib D-Bus Library
  *
  * Copyright (C) 2008-2010 Red Hat, Inc.
+ * Copyright (C) 2013 Samsung Electronics
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Lesser General Public
@@ -17,7 +18,9 @@
  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
  * Boston, MA 02111-1307, USA.
  *
- * Author: David Zeuthen <davidz at redhat.com>
+ * Author: David Zeuthen        <davidz at redhat.com>
+ * Author: Lukasz Skalski       <l.skalski at partner.samsung.com>
+ * Author: Michal Eljasiewicz   <m.eljasiewicz at samsung.com>
  */
 
 #include "config.h"
@@ -45,6 +48,7 @@
 #include "gsocketoutputstream.h"
 
 #ifdef G_OS_UNIX
+#include "gkdbusconnection.h"
 #include "gunixfdmessage.h"
 #include "gunixconnection.h"
 #include "gunixcredentialsmessage.h"
@@ -117,6 +121,108 @@ typedef struct
   gboolean from_mainloop;
 } ReadWithControlData;
 
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+typedef struct
+{
+  GKdbus *kdbus;
+  GCancellable *cancellable;
+
+  GSimpleAsyncResult *simple;
+
+  gboolean from_mainloop;
+} ReadKdbusData;
+
+static void
+read_kdbus_data_free (ReadKdbusData  *data)
+{
+  g_object_unref (data->kdbus);
+  if (data->cancellable != NULL)
+    g_object_unref (data->cancellable);
+  g_object_unref (data->simple);
+  g_free (data);
+}
+
+static gboolean
+_g_kdbus_read_ready (GKdbus        *kdbus,
+                     GIOCondition   condition,
+                     gpointer       user_data)
+{
+  ReadKdbusData *data = user_data;
+  GError *error;
+  gssize result;
+
+  error = NULL;
+
+  result = g_kdbus_receive (data->kdbus,
+                            data->cancellable,
+                            &error);
+  if (result >= 0)
+    {
+      g_simple_async_result_set_op_res_gssize (data->simple, result);
+    }
+  else
+    {
+      g_assert (error != NULL);
+      g_simple_async_result_take_error (data->simple, error);
+    }
+
+  if (data->from_mainloop)
+    g_simple_async_result_complete (data->simple);
+  else
+    g_simple_async_result_complete_in_idle (data->simple);
+
+  return FALSE;
+}
+
+static void
+_g_kdbus_read (GKdbus               *kdbus,
+               GCancellable         *cancellable,
+               GAsyncReadyCallback   callback,
+               gpointer              user_data)
+{
+  ReadKdbusData *data;
+  GSource *source;
+
+  data = g_new0 (ReadKdbusData, 1);
+  data->kdbus = g_object_ref (kdbus);
+  data->cancellable = cancellable != NULL ? g_object_ref (cancellable) : NULL;
+
+  data->simple = g_simple_async_result_new (G_OBJECT (kdbus),
+                                            callback,
+                                            user_data,
+                                            _g_kdbus_read);
+  g_simple_async_result_set_check_cancellable (data->simple, cancellable);
+
+  data->from_mainloop = TRUE;
+  source = g_kdbus_create_source (data->kdbus,
+                                   G_IO_IN,
+                                   cancellable);
+  g_source_set_callback (source,
+                         (GSourceFunc) _g_kdbus_read_ready,
+                         data,
+                         (GDestroyNotify) read_kdbus_data_free);
+  g_source_attach (source, g_main_context_get_thread_default ());
+  g_source_unref (source);
+}
+
+static gssize
+_g_kdbus_read_finish (GKdbus        *kdbus,
+                      GAsyncResult  *result,
+                      GError       **error)
+{
+  GSimpleAsyncResult *simple = G_SIMPLE_ASYNC_RESULT (result);
+
+  g_return_val_if_fail (G_IS_KDBUS (kdbus), -1);
+  g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == _g_kdbus_read);
+
+  if (g_simple_async_result_propagate_error (simple, error))
+      return -1;
+  else
+    return g_simple_async_result_get_op_res_gssize (simple);
+}
+
+#endif /* defined (G_OS_UNIX) && (KDBUS_TRANSPORT) */
+
 static void
 read_with_control_data_free (ReadWithControlData *data)
 {
@@ -364,8 +470,11 @@ struct GDBusWorker
   GDBusWorkerDisconnectedCallback     disconnected_callback;
   gpointer                            user_data;
 
-  /* if not NULL, stream is GSocketConnection */
+  /* if GSocket and GKdbus are NULL, stream is GSocketConnection */
   GSocket *socket;
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  GKdbus  *kdbus;
+#endif
 
   /* used for reading */
   GMutex                              read_lock;
@@ -506,7 +615,7 @@ _g_dbus_worker_emit_message_about_to_be_sent (GDBusWorker  *worker,
 }
 
 /* can only be called from private thread with read-lock held - takes ownership of @message */
-static void
+void
 _g_dbus_worker_queue_or_deliver_received_message (GDBusWorker  *worker,
                                                   GDBusMessage *message)
 {
@@ -584,7 +693,25 @@ _g_dbus_worker_do_read_cb (GInputStream  *input_stream,
     goto out;
 
   error = NULL;
-  if (worker->socket == NULL)
+
+  if (FALSE)
+    {
+    }
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  else if (G_IS_KDBUS_CONNECTION (worker->stream))
+    {
+      bytes_read = _g_kdbus_read_finish (worker->kdbus,
+                                         res,
+                                         &error);
+
+      /* Set read_buffer pointer to KDBUS memory pool */
+      worker->read_buffer = g_kdbus_get_msg_buffer_ptr (worker->kdbus);
+
+      /* For KDBUS transport we don't have to read message header */
+      worker->read_buffer_bytes_wanted = bytes_read;
+    }
+#endif
+  else if (worker->socket == NULL)
     bytes_read = g_input_stream_read_finish (g_io_stream_get_input_stream (worker->stream),
                                              res,
                                              &error);
@@ -819,6 +946,15 @@ _g_dbus_worker_do_read_cb (GInputStream  *input_stream,
  out:
   g_mutex_unlock (&worker->read_lock);
 
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  /* release memory occupied by kdbus_msg */
+  if (G_IS_KDBUS_CONNECTION (worker->stream) && !g_kdbus_is_closed (worker->kdbus))
+    {
+      g_kdbus_release_kmsg (worker->kdbus);
+      worker->read_buffer = NULL;
+    }
+#endif
+
   /* gives up the reference acquired when calling g_input_stream_read_async() */
   _g_dbus_worker_unref (worker);
 }
@@ -831,6 +967,23 @@ _g_dbus_worker_do_read_unlocked (GDBusWorker *worker)
    * true, because only failing a read causes us to signal 'closed'.
    */
 
+  /* For KDBUS transport we don't  have to alloc buffer, instead of it
+   * we use kdbus memory pool.   On connection stage KDBUS client have
+   * to register a  memory pool, large enough to  carry all backlog of
+   * data enqueued for the connection.
+   */
+
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  if (G_IS_KDBUS_CONNECTION (worker->stream))
+    {
+      _g_kdbus_read(worker->kdbus,
+                    worker->cancellable,
+                    (GAsyncReadyCallback) _g_dbus_worker_do_read_cb,
+                    _g_dbus_worker_ref (worker));
+      return;
+    }
+#endif
+
   /* if bytes_wanted is zero, it means start reading a message */
   if (worker->read_buffer_bytes_wanted == 0)
     {
@@ -997,6 +1150,26 @@ write_message_continue_writing (MessageToWriteData *data)
   simple = data->simple;
 #endif
 
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  if (G_IS_KDBUS_CONNECTION (data->worker->stream))
+    {
+      GError *error;
+      error = NULL;
+      data->total_written = g_kdbus_send_message(data->worker,
+                                                 data->worker->kdbus,
+                                                 data->message,
+                                                 data->blob,
+                                                 data->blob_size,
+                                                 data->worker->cancellable,
+                                                 &error);
+
+      write_message_print_transport_debug (data->total_written, data);
+      g_simple_async_result_complete (simple);
+      g_object_unref (simple);
+      goto out;
+    }
+#endif
+
   ostream = g_io_stream_get_output_stream (data->worker->stream);
 #ifdef G_OS_UNIX
   fd_list = g_dbus_message_get_unix_fd_list (data->message);
@@ -1452,9 +1625,17 @@ continue_writing (GDBusWorker *worker)
       worker->close_expected = TRUE;
       worker->output_pending = PENDING_CLOSE;
 
-      g_io_stream_close_async (worker->stream, G_PRIORITY_DEFAULT,
-                               NULL, iostream_close_cb,
-                               _g_dbus_worker_ref (worker));
+      if (FALSE)
+        {
+        }
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+      if (G_IS_KDBUS_CONNECTION (worker->stream))
+          g_kdbus_connection_close (worker->stream, NULL, NULL);
+#endif
+      else
+          g_io_stream_close_async (worker->stream, G_PRIORITY_DEFAULT,
+                                   NULL, iostream_close_cb,
+                                   _g_dbus_worker_ref (worker));
     }
   else
     {
@@ -1677,6 +1858,12 @@ _g_dbus_worker_new (GIOStream                              *stream,
   if (G_IS_SOCKET_CONNECTION (worker->stream))
     worker->socket = g_socket_connection_get_socket (G_SOCKET_CONNECTION (worker->stream));
 
+#if defined (G_OS_UNIX) && (KDBUS_TRANSPORT)
+  if (G_IS_KDBUS_CONNECTION (worker->stream))
+    worker->kdbus = g_kdbus_connection_get_kdbus (G_KDBUS_CONNECTION (worker->stream));
+#endif
+
+
   worker->shared_thread_data = _g_dbus_shared_thread_ref ();
 
   /* begin reading */
@@ -2156,12 +2343,11 @@ write_message_print_transport_debug (gssize bytes_written,
   g_print ("========================================================================\n"
            "GDBus-debug:Transport:\n"
            "  >>>> WROTE %" G_GSSIZE_FORMAT " bytes of message with serial %d and\n"
-           "       size %" G_GSIZE_FORMAT " from offset %" G_GSIZE_FORMAT " on a %s\n",
+           "       size %" G_GSIZE_FORMAT " from offset %" G_GSIZE_FORMAT "\n",
            bytes_written,
            g_dbus_message_get_serial (data->message),
            data->blob_size,
-           data->total_written,
-           g_type_name (G_TYPE_FROM_INSTANCE (g_io_stream_get_output_stream (data->worker->stream))));
+           data->total_written);
   _g_dbus_debug_print_unlock ();
  out:
   ;
@@ -2207,12 +2393,11 @@ read_message_print_transport_debug (gssize bytes_read,
   g_print ("========================================================================\n"
            "GDBus-debug:Transport:\n"
            "  <<<< READ %" G_GSSIZE_FORMAT " bytes of message with serial %d and\n"
-           "       size %d to offset %" G_GSIZE_FORMAT " from a %s\n",
+           "       size %d to offset %" G_GSIZE_FORMAT "\n",
            bytes_read,
            serial,
            message_length,
-           worker->read_buffer_cur_size,
-           g_type_name (G_TYPE_FROM_INSTANCE (g_io_stream_get_input_stream (worker->stream))));
+           worker->read_buffer_cur_size);
   _g_dbus_debug_print_unlock ();
  out:
   ;
diff --git a/gio/gdbusprivate.h b/gio/gdbusprivate.h
index 1bc503c..5b3046e 100644
--- a/gio/gdbusprivate.h
+++ b/gio/gdbusprivate.h
@@ -1,6 +1,7 @@
 /* GDBus - GLib D-Bus Library
  *
  * Copyright (C) 2008-2010 Red Hat, Inc.
+ * Copyright (C) 2013 Samsung Electronics
  *
  * This library is free software; you can redistribute it and/or
  * modify it under the terms of the GNU Lesser General Public
@@ -17,7 +18,9 @@
  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
  * Boston, MA 02111-1307, USA.
  *
- * Author: David Zeuthen <davidz at redhat.com>
+ * Author: David Zeuthen        <davidz at redhat.com>
+ * Author: Lukasz Skalski       <l.skalski at partner.samsung.com>
+ * Author: Michal Eljasiewicz   <m.eljasiewic at samsung.com>
  */
 
 #ifndef __G_DBUS_PRIVATE_H__
@@ -81,6 +84,9 @@ void         _g_dbus_worker_close        (GDBusWorker         *worker,
                                           GCancellable        *cancellable,
                                           GSimpleAsyncResult  *result);
 
+/* kdbus transport needs this function to generate local messages */
+void         _g_dbus_worker_queue_or_deliver_received_message (GDBusWorker  *worker,
+                                                               GDBusMessage *message);
 /* ---------------------------------------------------------------------------------------------------- */
 
 void _g_dbus_initialize (void);
diff --git a/gio/giotypes.h b/gio/giotypes.h
index 61f78a0..d2f2c92 100644
--- a/gio/giotypes.h
+++ b/gio/giotypes.h
@@ -254,6 +254,23 @@ typedef struct _GVolume                       GVolume; /* Dummy typedef */
 typedef struct _GVolumeMonitor                GVolumeMonitor;
 
 /**
+ * GKdbus:
+ *
+ * A lowlevel kdbus object.
+ *
+ **/
+
+typedef struct _GKdbus                        GKdbus;
+
+/**
+ * GKdbusConnection:
+ *
+ * A kdbus connection GIOStream object.
+ *
+ **/
+typedef struct _GKdbusConnection              GKdbusConnection;
+
+/**
  * GAsyncReadyCallback:
  * @source_object: the object the asynchronous operation was started with.
  * @res: a #GAsyncResult.
@@ -390,6 +407,22 @@ typedef gboolean (*GSocketSourceFunc) (GSocket *socket,
 				       gpointer user_data);
 
 /**
+ * GKdbusSourceFunc:
+ * @socket: the #GKdbus
+ * @condition: the current condition at the source fired.
+ * @user_data: data passed in by the user.
+ *
+ * This is the function type of the callback used for the #GSource
+ * returned by g_kdbus_create_source().
+ *
+ * Returns: it should return %FALSE if the source should be removed.
+ *
+ */
+typedef gboolean (*GKdbusSourceFunc) (GKdbus *kdbus,
+                                      GIOCondition condition,
+                                      gpointer user_data);
+
+/**
  * GInputVector:
  * @buffer: Pointer to a buffer where data will be written.
  * @size: the available size in @buffer.
-- 
1.8.4.rc3



More information about the systemd-devel mailing list