[gnio/connection-factory: 7/8] Merge branch 'master' into connection-factory



commit dc6383ca0b55cdc0b9bcac056cd8a6608bb02c38
Merge: 9247ac0... b6d42bb...
Author: Alexander Larsson <alexl redhat com>
Date:   Thu May 14 18:46:42 2009 +0200

    Merge branch 'master' into connection-factory
    
    Conflicts:
    	gio/Makefile.am
    	gio/gsocket.c
    	gio/gsocket.h
    	gio/gsocketclient.c
    	gio/gsocketlistener.c
    	gio/gtcpclient.c
    	gio/gtcplistener.c
    	gio/gunixclient.c
    	gio/gunixlistener.c

 configure.ac                |   49 +-
 gio/Makefile.am             |   16 +-
 gio/gasyncinitable.c        |  377 ------
 gio/gasyncinitable.h        |  120 --
 gio/ginitable.c             |  245 ----
 gio/ginitable.h             |   96 --
 gio/giostream.c             |  524 --------
 gio/giostream.h             |  113 --
 gio/gnio.h                  |    4 -
 gio/gnioerror.h             |   41 -
 gio/gsocket.c               | 2973 -------------------------------------------
 gio/gsocket.h               |  256 ----
 gio/gsocketclient.c         |    5 +-
 gio/gsocketcontrolmessage.c |  192 ---
 gio/gsocketcontrolmessage.h |   90 --
 gio/gsocketlistener.c       |    5 +-
 gio/gtls.h                  |    2 +-
 gio/gunixfdmessage.c        |  252 ----
 gio/gunixfdmessage.h        |   58 -
 test/server.c               |    5 +-
 20 files changed, 9 insertions(+), 5414 deletions(-)

diff --cc gio/Makefile.am
index ce38509,cf2e468..bf4346f
--- a/gio/Makefile.am
+++ b/gio/Makefile.am
@@@ -30,8 -27,9 +25,7 @@@ sources = 
  
  if OS_UNIX
  unix_sources = \
- 	gunixconnection.c		\
- 	gunixfdmessage.c
 -	gunixclient.c			\
 -	gunixconnection.c		\
 -	gunixlistener.c
++	gunixconnection.c		
  else
  unix_sources =
  endif
@@@ -45,22 -43,18 +39,14 @@@ endi
  gioincludedir = $(includedir)/gnio/gio
  
  headers = \
- 	giostream.h			\
  	gnio.h				\
- 	gnioconfig.h			\
- 	gnioerror.h			\
- 	gasyncinitable.h		\
- 	ginitable.h			\
- 	gsocket.h			\
  	gsocketclient.h			\
  	gsocketconnection.h		\
- 	gsocketcontrolmessage.h		\
  	gsocketlistener.h		\
  	gsocketservice.h		\
 -	gtcpclient.h			\
  	gtcpconnection.h		\
 -	gtcplistener.h			\
  	gthreadedsocketservice.h	\
- 	gunixfdmessage.h		\
 -	gunixclient.h			\
 -	gunixconnection.h		\
 -	gunixlistener.h
 +	gunixconnection.h
  
  gioinclude_HEADERS = $(headers) gnioenums.h
  
diff --cc gio/gsocketclient.c
index a5060dd,7b270b8..40bf524
--- a/gio/gsocketclient.c
+++ b/gio/gsocketclient.c
@@@ -37,62 -27,17 +37,63 @@@
  #include <gio/gsimpleasyncresult.h>
  #include <gio/gcancellable.h>
  #include <gio/gioerror.h>
 +#include <gio/gnetworkaddress.h>
- #include "gsocket.h"
+ #include <gio/gsocketaddress.h>
  
  G_DEFINE_TYPE (GSocketClient, g_socket_client, G_TYPE_OBJECT);
  
 +enum
 +{
 +  PROP_NONE,
 +  PROP_FAMILY,
 +  PROP_TYPE,
 +  PROP_PROTOCOL,
 +  PROP_LOCAL_ADDRESS
 +};
 +
 +struct _GSocketClientPrivate
 +{
 +  GSocketFamily family;
 +  GSocketType type;
 +  char *protocol;
 +  GSocketAddress *local_address;
 +};
 +
  static GSocket *
 -g_socket_client_real_socket_factory (GSocketClient  *client,
 -                                     GSocketAddress *address,
 -				     GError        **error)
 +create_socket (GSocketClient  *client,
 +	       GSocketAddress *dest_address,
 +	       GError        **error)
  {
 -  return g_socket_new (g_socket_address_get_family (address),
 -                       G_SOCKET_TYPE_STREAM, NULL, error);
 +  GSocketFamily family;
 +  GSocket *socket;
 +
 +  family = client->priv->family;
 +  if (family == G_SOCKET_FAMILY_INVALID &&
 +      client->priv->local_address != NULL)
 +    family = g_socket_address_get_family (client->priv->local_address);
 +  if (family == G_SOCKET_FAMILY_INVALID)
 +    family = g_socket_address_get_family (dest_address);
 +
 +  socket = g_socket_new (family,
 +			 client->priv->type,
 +			 client->priv->protocol,
 +			 error);
 +  if (socket == NULL)
 +    return NULL;
 +
 +  if (client->priv->local_address)
 +    {
 +      if (!g_socket_bind (socket,
 +			  client->priv->local_address,
++			  FALSE,
 +			  error))
 +	{
 +	  g_object_unref (socket);
 +	  return NULL;
 +	}
 +    }
 +
 +  return socket;
  }
  
  static void
@@@ -526,17 -145,9 +527,17 @@@ g_socket_client_enumerator_callback (GO
  				     GAsyncResult *result,
  				     gpointer      user_data);
  
 +static void
 +set_last_error (GSocketClientAsyncConnectData *data,
 +		GError *error)
 +{
 +  g_clear_error (&data->last_error);
 +  data->last_error = error;
 +}
 +
  static gboolean
  g_socket_client_socket_callback (GSocket *socket,
-                                  GIOCondition condition,
+ 				 GIOCondition condition,
  				 GSocketClientAsyncConnectData *data)
  {
    GError *error = NULL;
diff --cc gio/gsocketlistener.c
index db964bd,e0ddf17..9ac7299
--- a/gio/gsocketlistener.c
+++ b/gio/gsocketlistener.c
@@@ -25,31 -25,19 +25,30 @@@
  
  #include "gsocketlistener.h"
  
 +#include "config.h"
  #include <gio/gsimpleasyncresult.h>
  #include <gio/gcancellable.h>
- #include <gio/gioerror.h>
++#include <gio/gsocketaddress.h>
 +#include <gio/ginetaddress.h>
 +#include <gio/ginetsocketaddress.h>
- #include "gsocket.h"
  
 -G_DEFINE_ABSTRACT_TYPE (GSocketListener, g_socket_listener, G_TYPE_OBJECT);
 +G_DEFINE_TYPE (GSocketListener, g_socket_listener, G_TYPE_OBJECT);
  
 -struct _GSocketListenerPrivate
 +enum
  {
 -  GSocket            *socket;
 -  GError             *error;
 +  PROP_0,
 +  PROP_LISTEN_BACKLOG
 +};
 +
  
 -  GSimpleAsyncResult *result;
 -  GCancellable       *cancellable;
 -  gboolean            from_mainloop;
 +static GQuark source_quark = 0;
 +
 +struct _GSocketListenerPrivate
 +{
 +  GPtrArray           *sockets;
 +  GMainContext        *main_context;
 +  int                 listen_backlog;
 +  guint               closed : 1;
  };
  
  static void
@@@ -131,303 -83,53 +130,303 @@@ g_socket_listener_class_init (GSocketLi
  }
  
  static void
 -g_socket_listener_init (GSocketListener *server)
 +g_socket_listener_init (GSocketListener *listener)
  {
 -  server->priv = G_TYPE_INSTANCE_GET_PRIVATE (server,
 -                                              G_TYPE_SOCKET_LISTENER,
 -                                              GSocketListenerPrivate);
 +  listener->priv = G_TYPE_INSTANCE_GET_PRIVATE (listener,
 +						G_TYPE_SOCKET_LISTENER,
 +						GSocketListenerPrivate);
 +  listener->priv->sockets =
 +    g_ptr_array_new_with_free_func ((GDestroyNotify) g_object_unref);
 +  listener->priv->listen_backlog = 10;
  }
  
 -GSocketConnection *
 -g_socket_listener_accept (GSocketListener  *listener,
 -                          GCancellable     *cancellable,
 -                          GError          **error)
 +GSocketListener *
 +g_socket_listener_new (void)
 +{
 +  return g_object_new (G_TYPE_SOCKET_LISTENER, NULL);
 +}
 +
 +static gboolean
 +check_listener (GSocketListener *listener,
 +		GError **error)
 +{
 +  if (listener->priv->closed)
 +    {
 +      g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED,
 +			   _("Listener is already closed"));
 +      return FALSE;
 +    }
 +
 +  return TRUE;
 +}
 +
 +gboolean
 +g_socket_listener_add_socket (GSocketListener *listener,
 +			      GSocket *socket,
 +			      GObject *source_object,
 +			      GError **error)
 +{
 +  if (!check_listener (listener, error))
 +    return FALSE;
 +
 +  /* TODO: Check that socket it is bound & not closed? */
 +
 +  if (g_socket_is_closed (socket))
 +    {
 +      g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED,
 +			   _("Added socket is closed"));
 +      return FALSE;
 +    }
 +
 +  g_ptr_array_add (listener->priv->sockets, socket);
 +  g_socket_set_listen_backlog (socket, listener->priv->listen_backlog);
 +
 +  if (source_object)
 +    g_object_set_qdata_full (G_OBJECT (socket), source_quark,
 +			     g_object_ref (source_object), g_object_unref);
 +
 +  return TRUE;
 +}
 +
 +gboolean
 +g_socket_listener_add_address (GSocketListener *listener,
 +			       GSocketAddress *address,
 +			       GSocketType type,
 +			       const char *protocol,
 +			       GObject *source_object,
 +			       GError **error)
  {
 +  GSocketFamily family;
    GSocket *socket;
  
 -  g_return_val_if_fail (G_IS_SOCKET_LISTENER (listener), NULL);
 +  if (!check_listener (listener, error))
 +    return FALSE;
 +
 +  family = g_socket_address_get_family (address);
 +  socket = g_socket_new (family, type, protocol, error);
 +  if (socket == NULL)
 +    return FALSE;
 +
-   if (!g_socket_bind (socket, address, error) ||
++  if (!g_socket_bind (socket, address, TRUE, error) ||
 +      !g_socket_listen (socket, error) ||
 +      !g_socket_listener_add_socket (listener, socket,
 +				     source_object,
 +				     error))
 +    {
 +      g_object_unref (socket);
 +      return FALSE;
 +    }
 +
 +  if (G_SOCKET_LISTENER_GET_CLASS (listener)->changed)
 +    G_SOCKET_LISTENER_GET_CLASS (listener)->changed (listener);
 +
 +  return TRUE;
 +}
 +
 +gboolean
 +g_socket_listener_add_inet_port (GSocketListener *listener,
 +				 int port,
 +				 GObject *source_object,
 +				 GError **error)
 +{
 +  GSocketAddress *address4, *address6;
 +  GInetAddress *inet_address;
 +  gboolean res;
 +
 +  if (!check_listener (listener, error))
 +    return FALSE;
 +
 +  inet_address = g_inet_address_new_any (G_SOCKET_FAMILY_IPV4);
 +  address4 = g_inet_socket_address_new (inet_address, port);
 +  g_object_unref (inet_address);
 +
 +  inet_address = g_inet_address_new_any (G_SOCKET_FAMILY_IPV6);
 +  address6 = g_inet_socket_address_new (inet_address, port);
 +  g_object_unref (inet_address);
 +
 +  if (!g_socket_listener_add_address (listener,
 +				      address6,
 +				      G_SOCKET_TYPE_STREAM,
 +				      NULL,
 +				      source_object,
 +				      NULL))
 +    {
 +      /* Failed, to create ipv6, socket, just use ipv4,
 +	 return any error */
 +      res = g_socket_listener_add_address (listener,
 +					   address4,
 +					   G_SOCKET_TYPE_STREAM,
 +					   NULL,
 +					   source_object,
 +					   error);
 +    }
 +  else
 +    {
 +      /* Succeeded with ipv6, also try ipv4 in case its ipv6 only,
 +	 but ignore errors here */
 +      res = TRUE;
 +      g_socket_listener_add_address (listener,
 +				     address4,
 +				     G_SOCKET_TYPE_STREAM,
 +				     NULL,
 +				     source_object,
 +				     NULL);
 +    }
 +
 +  g_object_unref (address4);
 +  g_object_unref (address6);
 +
 +  return res;
 +}
 +
 +static GList *
 +add_sources (GSocketListener *listener,
 +	     GSocketSourceFunc callback,
 +	     gpointer callback_data,
 +	     GCancellable *cancellable,
 +	     GMainContext *context)
 +{
 +  GSocket *socket;
 +  GSource *source;
 +  GList *sources;
 +  int i;
  
 -  if (listener->priv->error)
 +  sources = NULL;
 +  for (i = 0; i < listener->priv->sockets->len; i++)
      {
 -      if (error)
 -        *error = g_error_copy (listener->priv->error);
 +      socket = listener->priv->sockets->pdata[i];
 +
 +      source = g_socket_create_source (socket, G_IO_IN, cancellable);
 +      g_source_set_callback (source,
 +                             (GSourceFunc) callback,
 +                             callback_data, NULL);
 +      g_source_attach (source, context);
 +
 +      sources = g_list_prepend (sources, source);
 +    }
 +
 +  return sources;
 +}
 +
 +static void
 +free_sources (GList *sources)
 +{
 +  GSource *source;
 +  while (sources != NULL)
 +    {
 +      source = sources->data;
 +      sources = g_list_delete_link (sources, sources);
 +      g_source_destroy (source);
 +      g_source_unref (source);
 +    }
 +}
 +
 +struct AcceptData {
 +  GMainLoop *loop;
 +  GSocket *socket;
 +};
 +
 +static gboolean
 +accept_callback (GSocket *socket,
 +		 GIOCondition condition,
 +		 gpointer user_data)
 +{
 +  struct AcceptData *data = user_data;
 +
 +  data->socket = socket;
 +  g_main_loop_quit (data->loop);
  
 -      return NULL;
 +  return TRUE;
 +}
 +
 +GSocket *
 +g_socket_listener_accept_socket (GSocketListener  *listener,
 +				 GCancellable     *cancellable,
 +				 GObject         **source_object,
 +				 GError          **error)
 +{
 +  GSocket *accept_socket, *socket;
 +
 +  g_return_val_if_fail (G_IS_SOCKET_LISTENER (listener), NULL);
 +
 +  if (!check_listener (listener, error))
 +    return NULL;
 +
 +  if (listener->priv->sockets->len == 1)
 +    {
 +      accept_socket = listener->priv->sockets->pdata[0];
 +      if (!g_socket_condition_wait (accept_socket, G_IO_IN,
 +				    cancellable, error))
 +	return NULL;
 +    }
 +  else
 +    {
 +      GList *sources;
 +      struct AcceptData data;
 +      GMainLoop *loop;
 +
 +      if (listener->priv->main_context == NULL)
 +	listener->priv->main_context = g_main_context_new ();
 +
 +      loop = g_main_loop_new (listener->priv->main_context, FALSE);
 +      data.loop = loop;
 +      sources = add_sources (listener,
 +			     accept_callback,
 +			     &data,
 +			     cancellable,
 +			     listener->priv->main_context);
 +      g_main_loop_run (loop);
 +      accept_socket = data.socket;
 +      free_sources (sources);
 +      g_main_loop_unref (loop);
      }
  
 -  if (!g_socket_condition_wait (listener->priv->socket, G_IO_IN,
 -                                cancellable, error))
 +  if (!(socket = g_socket_accept (accept_socket, error)))
      return NULL;
  
 -  if (!(socket = g_socket_accept (listener->priv->socket, error)))
 +  if (source_object)
 +    *source_object = g_object_get_qdata (G_OBJECT (accept_socket), source_quark);
 +
 +  return socket;
 +}
 +
 +GSocketConnection *
 +g_socket_listener_accept (GSocketListener  *listener,
 +			  GCancellable     *cancellable,
 +			  GObject         **source_object,
 +			  GError          **error)
 +{
 +  GSocketConnection *connection;
 +  GSocket *socket;
 +
 +  socket = g_socket_listener_accept_socket (listener,
 +					    cancellable,
 +					    source_object,
 +					    error);
 +  if (socket == NULL)
      return NULL;
  
 -  return G_SOCKET_LISTENER_GET_CLASS (listener)
 -    ->connection_factory (listener, socket);
 +  connection = g_socket_connection_factory_create_connection (socket);
 +  g_object_unref (socket);
 +
 +  return connection;
  }
  
 +struct AcceptAsyncData {
 +  GSimpleAsyncResult *simple;
 +  GCancellable *cancellable;
 +  GList *sources;
 +};
 +
  static gboolean
 -g_socket_listener_accept_ready (GSocket *socket,
 -                                GIOCondition     condition,
 -				GSocketListener *listener)
 +accept_ready (GSocket *accept_socket,
 +	      GIOCondition condition,
 +	      gpointer _data)
  {
 -  GSimpleAsyncResult *simple;
 +  struct AcceptAsyncData *data = _data;
    GError *error = NULL;
  
 -  simple = listener->priv->result;
 -  listener->priv->result = NULL;
 -
 -  if (!g_cancellable_set_error_if_cancelled (listener->priv->cancellable,
 +  if (!g_cancellable_set_error_if_cancelled (data->cancellable,
                                               &error))
      {
        GSocket *socket;



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]