[Galago-commits] r2830 - in trunk/libgalago: . docs/reference docs/reference/tmpl libgalago

galago-commits at freedesktop.org galago-commits at freedesktop.org
Sun Jun 11 18:40:34 PDT 2006


Author: chipx86
Date: 2006-06-11 18:40:22 -0700 (Sun, 11 Jun 2006)
New Revision: 2830

Modified:
   trunk/libgalago/ChangeLog
   trunk/libgalago/docs/reference/libgalago-sections.txt
   trunk/libgalago/docs/reference/tmpl/galago-service.sgml
   trunk/libgalago/libgalago/galago-dbus.c
   trunk/libgalago/libgalago/galago-dbus.h
   trunk/libgalago/libgalago/galago-object.h
   trunk/libgalago/libgalago/galago-service.c
   trunk/libgalago/libgalago/galago-service.h
Log:
Added the beginning of the async functionality:
- Put in a stubbed out galago_service_get_account_async() and galago_dbus_send_message_with_reply_async().
- Modified galago_dbus_send_message_with_reply_list_vargs() to handle sending messages and receiving replies both synchronously and asynchronously.


Modified: trunk/libgalago/ChangeLog
===================================================================
--- trunk/libgalago/ChangeLog	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/ChangeLog	2006-06-12 01:40:22 UTC (rev 2830)
@@ -1,3 +1,19 @@
+Sun Jun 11 18:16:36 PDT 2006  Christian Hammond <chipx86 at chipx86.com>
+
+	* docs/reference/libgalago-sections.txt:
+	* docs/reference/tmpl/galago-service.sgml:
+	* libgalago/galago-dbus.c:
+	* libgalago/galago-dbus.h:
+	* libgalago/galago-object.h:
+	* libgalago/galago-service.c:
+	* libgalago/galago-service.h:
+	  - Added the beginning of the async functionality:
+	    - Put in a stubbed out galago_service_get_account_async() and
+	      galago_dbus_send_message_with_reply_async().
+	    - Modified galago_dbus_send_message_with_reply_list_vargs() to
+		  handle sending messages and receiving replies both synchronously
+	      and asynchronously.
+
 Mon May 22 01:26:17 PDT 2006  Christian Hammond <chipx86 at chipx86.com>
 
 	* libgalago/galago-service.c:

Modified: trunk/libgalago/docs/reference/libgalago-sections.txt
===================================================================
--- trunk/libgalago/docs/reference/libgalago-sections.txt	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/docs/reference/libgalago-sections.txt	2006-06-12 01:40:22 UTC (rev 2830)
@@ -253,6 +253,7 @@
 galago_service_get_flags
 galago_service_create_account
 galago_service_get_account
+galago_service_get_account_async
 galago_service_get_accounts
 galago_service_normalize
 <SUBSECTION Standard>

Modified: trunk/libgalago/docs/reference/tmpl/galago-service.sgml
===================================================================
--- trunk/libgalago/docs/reference/tmpl/galago-service.sgml	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/docs/reference/tmpl/galago-service.sgml	2006-06-12 01:40:22 UTC (rev 2830)
@@ -220,6 +220,19 @@
 @Returns: 
 
 
+<!-- ##### FUNCTION galago_service_get_account_async ##### -->
+<para>
+
+</para>
+
+ at service: 
+ at username: 
+ at cb: 
+ at user_data: 
+ at error: 
+ at Returns: 
+
+
 <!-- ##### FUNCTION galago_service_get_accounts ##### -->
 <para>
 

Modified: trunk/libgalago/libgalago/galago-dbus.c
===================================================================
--- trunk/libgalago/libgalago/galago-dbus.c	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/libgalago/galago-dbus.c	2006-06-12 01:40:22 UTC (rev 2830)
@@ -25,6 +25,32 @@
 #include <string.h>
 #include <stdio.h>
 
+typedef void (*PendingCallCb)(const GalagoObject *, GList *, gpointer);
+
+typedef struct
+{
+	const GalagoObject *object;
+	char *name;
+	GList *return_types;
+	PendingCallCb cb;
+	gpointer user_data;
+
+} PendingCallData;
+
+static void
+pending_call_data_free(PendingCallData *data)
+{
+	if (data->return_types != NULL)
+	{
+		g_list_foreach(data->return_types, (GFunc)galago_value_destroy, NULL);
+		g_list_free(data->return_types);
+	}
+
+	g_free(data->name);
+	g_free(data);
+}
+
+
 /**
  * galago_dbus_message_iter_append_string_or_nil
  * @iter: The message iterator.
@@ -650,16 +676,94 @@
 }
 
 static GList *
+message_reply_received_cb(DBusMessage *message, GList *return_types)
+{
+	GList *ret_list = NULL, *l;
+	DBusMessageIter iter;
+
+	dbus_message_iter_init(message, &iter);
+
+	for (l = return_types; l != NULL; l = l->next)
+	{
+		ret_list = g_list_append(ret_list,
+			get_ret_val_from_iter(&iter, (GalagoValue *)l->data));
+
+		dbus_message_iter_next(&iter);
+	}
+
+	if (return_types != NULL)
+	{
+		g_list_foreach(return_types, (GFunc)galago_value_destroy, NULL);
+		g_list_free(return_types);
+	}
+
+	return ret_list;
+}
+
+static void
+handle_pending_call_error(const GalagoObject *object, const char *name,
+						  DBusError *error)
+{
+	if (!dbus_error_has_name(error, GALAGO_DBUS_ERROR_OBJECT_NOT_FOUND))
+	{
+		g_warning("Error sending %s.%s: %s",
+				  g_type_name(G_OBJECT_TYPE(object)),
+				  name, error->message);
+	}
+}
+
+static void
+pending_call_done_cb(DBusPendingCall *call, gpointer user_data)
+{
+	PendingCallData *call_data = (PendingCallData *)user_data;
+	DBusMessage *reply = NULL;
+	GList *ret_list;
+
+	if (!dbus_pending_call_get_completed(call))
+		goto exit;
+
+	reply = dbus_pending_call_steal_reply(call);
+
+	if (reply == NULL)
+		goto exit;
+
+	if (dbus_message_get_type(reply) == DBUS_MESSAGE_TYPE_ERROR)
+	{
+		DBusError error;
+
+		dbus_error_init(&error);
+		dbus_set_error_from_message(&error, reply);
+		handle_pending_call_error(call_data->object, call_data->name, &error);
+		dbus_error_free(&error);
+
+		goto exit;
+	}
+
+	ret_list = message_reply_received_cb(reply, call_data->return_types);
+	call_data->cb(call_data->object, ret_list, call_data->user_data);
+
+	/* Hack to prevent this from being freed later. */
+	call_data->return_types = NULL;
+
+exit:
+	if (reply != NULL)
+		dbus_message_unref(reply);
+
+	dbus_pending_call_unref(call);
+	pending_call_data_free(call_data);
+}
+
+static GList *
 galago_dbus_send_message_with_reply_list_vargs(const GalagoObject *object,
 											   const char *name,
 											   GList *return_types,
-											   va_list args)
+											   va_list args,
+											   PendingCallCb cb,
+											   gpointer user_data)
 {
-	DBusMessage *message;
-	DBusMessage *reply = NULL;
-	DBusMessageIter iter;
+	DBusMessage *message = NULL;
 	DBusError error;
-	GList *ret_list = NULL, *l;
+	GList *ret_list = NULL;
 
 	galago_goto_if_fail(object != NULL,           exit);
 	galago_goto_if_fail(name   != NULL,           exit);
@@ -677,45 +781,47 @@
 
 	galago_goto_if_fail(message != NULL, exit);
 
-	reply = dbus_connection_send_with_reply_and_block(
-		galago_get_dbus_conn(), message, -1, &error);
+	if (cb == NULL)
+	{
+		/* Synchronous */
+		DBusMessage *reply;
 
-	dbus_message_unref(message);
+		reply = dbus_connection_send_with_reply_and_block(
+			galago_get_dbus_conn(), message, -1, &error);
 
-	if (dbus_error_is_set(&error))
-	{
-		if (!dbus_error_has_name(&error, GALAGO_DBUS_ERROR_OBJECT_NOT_FOUND))
+		if (dbus_error_is_set(&error))
 		{
-			g_warning("Error sending %s.%s: %s",
-					  g_type_name(G_OBJECT_TYPE(object)),
-					  name, error.message);
+			handle_pending_call_error(object, name, &error);
+			goto exit;
 		}
 
-		goto exit;
+		ret_list = message_reply_received_cb(reply, return_types);
 	}
+	else
+	{
+		/* Asynchronous */
+		DBusPendingCall *call = NULL;
+		PendingCallData *call_data;
 
-	dbus_message_iter_init(reply, &iter);
+		call_data = g_new0(PendingCallData, 1);
+		call_data->object = object;
+		call_data->name = g_strdup(name);
+		call_data->return_types = return_types;
+		call_data->cb = cb;
+		call_data->user_data = user_data;
 
-	for (l = return_types; l != NULL; l = l->next)
-	{
-		ret_list = g_list_append(ret_list,
-			get_ret_val_from_iter(&iter, (GalagoValue *)l->data));
-
-		dbus_message_iter_next(&iter);
+		dbus_connection_send_with_reply(galago_get_dbus_conn(),
+										message, &call, -1);
+		dbus_pending_call_set_notify(call, pending_call_done_cb, call_data,
+									 (DBusFreeFunction)pending_call_data_free);
 	}
 
 exit:
+	if (message != NULL)
+		dbus_message_unref(message);
+
 	dbus_error_free(&error);
 
-	if (reply != NULL)
-		dbus_message_unref(reply);
-
-	if (return_types != NULL)
-	{
-		g_list_foreach(return_types, (GFunc)galago_value_destroy, NULL);
-		g_list_free(return_types);
-	}
-
 	return ret_list;
 }
 
@@ -744,7 +850,8 @@
 
 	va_start(args, return_types);
 	list = galago_dbus_send_message_with_reply_list_vargs(object, name,
-														  return_types, args);
+														  return_types, args,
+														  NULL, NULL);
 	va_end(args);
 
 	return list;
@@ -775,7 +882,7 @@
 
 	va_start(args, return_type);
 	list = galago_dbus_send_message_with_reply_list_vargs(
-		object, name, g_list_append(NULL, return_type), args);
+		object, name, g_list_append(NULL, return_type), args, NULL, NULL);
 	va_end(args);
 
 	if (list != NULL)
@@ -788,6 +895,24 @@
 	return retval;
 }
 
+GalagoCallHandle
+galago_dbus_send_message_with_reply_async(const GalagoObject *object,
+										  const char *name,
+										  GCallback cb, gpointer user_data,
+										  GalagoValue *return_type, ...)
+{
+	va_list args;
+	GalagoCallHandle handle = 1; /* XXX */
+	GList *return_types = NULL;
+
+	va_start(args, return_type);
+	return_types = g_list_append(return_types, return_type);
+	va_end(args);
+
+	return handle;
+}
+
+
 /**
  * galago_dbus_object_push_full
  * @object: The object to push.

Modified: trunk/libgalago/libgalago/galago-dbus.h
===================================================================
--- trunk/libgalago/libgalago/galago-dbus.h	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/libgalago/galago-dbus.h	2006-06-12 01:40:22 UTC (rev 2830)
@@ -67,6 +67,12 @@
 void *galago_dbus_send_message_with_reply(const GalagoObject *object,
 										  const char *name,
 										  GalagoValue *return_type, ...);
+GalagoCallHandle galago_dbus_send_message_with_reply_async(
+	const GalagoObject *object,
+	const char *name,
+	GCallback cb,
+	gpointer user_data,
+	GalagoValue *cb_param_type_1, ...);
 
 void galago_dbus_object_push_full(GalagoObject *object);
 

Modified: trunk/libgalago/libgalago/galago-object.h
===================================================================
--- trunk/libgalago/libgalago/galago-object.h	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/libgalago/galago-object.h	2006-06-12 01:40:22 UTC (rev 2830)
@@ -122,6 +122,9 @@
 #define GALAGO_OBJECT_IS_REMOTE(obj) \
 	(galago_object_get_origin(GALAGO_OBJECT(obj)) == GALAGO_REMOTE)
 
+typedef guint GalagoCallHandle;
+#define GALAGO_CALL_HANDLE_INVALID ((GalagoCallHandle)0)
+
 #include <libgalago/galago-context-base.h>
 
 G_BEGIN_DECLS

Modified: trunk/libgalago/libgalago/galago-service.c
===================================================================
--- trunk/libgalago/libgalago/galago-service.c	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/libgalago/galago-service.c	2006-06-12 01:40:22 UTC (rev 2830)
@@ -634,6 +634,7 @@
 
 	g_return_val_if_fail(service  != NULL,           NULL);
 	g_return_val_if_fail(username != NULL,           NULL);
+	g_return_val_if_fail(*username != '\0',          NULL);
 	g_return_val_if_fail(GALAGO_IS_SERVICE(service), NULL);
 
 	norm_username = galago_service_normalize(service, username);
@@ -659,6 +660,101 @@
 }
 
 /**
+ * galago_service_get_account_async
+ * @service:   The service.
+ * @username:  The account's username.
+ * @cb:        The callback function that will be passed the account.
+ * @user_data: Custom data to pass to the callback function.
+ *
+ * Asynchronously retrieves the account with the specified username from
+ * a service.
+ *
+ * For example:
+ * <informalexample>
+ * <programlisting>
+ *  static void
+ *  account_received_cb(const GalagoService *service,
+ *                      GalagoAccount *account,
+ *                      gpointer user_data)
+ *  {
+ *  }
+ *  
+ *  static void
+ *  get_bob_account(GalagoService *service)
+ *  {
+ *      GalagoCallHandle handle;
+ *  
+ *      handle = galago_service_get_account(service, "Bob",
+ *                                          account_received_cb, NULL, NULL);
+ *  }
+ * </programlisting>
+ * </informalexample>
+ *
+ * Returns: A valid #GalagoCallHandle on success. On error, this will return
+ *          %GALAGO_CALL_HANDLE_INVALID.
+ *
+ * Since: 0.5.2
+ */
+GalagoCallHandle
+galago_service_get_account_async(const GalagoService *service,
+								 const char *username,
+								 GCallback cb,
+								 gpointer user_data)
+{
+	GalagoAccount *account;
+	GalagoCallHandle handle = GALAGO_CALL_HANDLE_INVALID;
+
+	g_return_val_if_fail(service  != NULL,                      handle);
+	g_return_val_if_fail(GALAGO_IS_SERVICE(service),            handle);
+	g_return_val_if_fail(username != NULL && *username != '\0', handle);
+	g_return_val_if_fail(cb != NULL,                            handle);
+
+	account = galago_service_get_account(service, username, FALSE);
+
+	if (account != NULL)
+	{
+		((void (*)(const GalagoService *, GalagoAccount *, gpointer))cb)(
+			service, account, user_data);
+		//handle = galago_calls_request_dummy_handle();
+		handle = 1;
+	}
+	else if (GALAGO_OBJECT_IS_REMOTE(service) && !galago_is_daemon() &&
+			 !galago_is_connected())
+	{
+#if 0
+		DBusMessage *message;
+		DBusPendingCall *call;
+		GalagoClosure *closure;
+
+		message = galago_dbus_message_new_method_call_args(
+			GALAGO_OBJECT(service), "GetAccount", TRUE,
+			galago_value_new(GALAGO_VALUE_TYPE_STRING, &username, NULL),
+			NULL);
+
+		g_return_val_if_fail(message != NULL, GALAGO_CALL_HANDLE_INVALID);
+
+		/* TODO: Assign a call handle to return. */
+		handle = 1;
+		dbus_connection_send_with_reply(galago_get_dbus_conn(), message,
+										&call, -1);
+		dbus_message_unref(message);
+		//handle = galago_calls_request_handle(call);
+
+		closure = (GalagoClosure *)g_closure_new_simple(sizeof(GalagoClosure),
+														user_data);
+		closure->callback = cb;
+		closure->src_object = GALAGO_OBJECT(service);
+		g_closure_set_marshal((GClosure *)closure,
+							  g_cclosure_marshal_VOID__POINTER);
+
+		dbus_pending_call_set_notify(call, _happy_notify_func, closure, g_free);
+#endif
+	}
+
+	return handle;
+}
+
+/**
  * galago_service_get_accounts
  * @service: The service.
  * @query:   TRUE if a remote query should be done if there is no

Modified: trunk/libgalago/libgalago/galago-service.h
===================================================================
--- trunk/libgalago/libgalago/galago-service.h	2006-06-11 01:34:37 UTC (rev 2829)
+++ trunk/libgalago/libgalago/galago-service.h	2006-06-12 01:40:22 UTC (rev 2830)
@@ -127,6 +127,10 @@
 GalagoAccount *galago_service_get_account(const GalagoService *service,
 										  const char *username,
 										  gboolean query);
+GalagoCallHandle galago_service_get_account_async(const GalagoService *service,
+												  const char *username,
+												  GCallback cb,
+												  gpointer user_data);
 GList *galago_service_get_accounts(const GalagoService *service,
 								   gboolean query);
 



More information about the galago-commits mailing list