gio-querymodules: Call setlocale in main function
[glib.git] / gio / gsocketconnection.c
blob4918279d21178862d9ec5bcc09950bab9555d8fd
1 /* GIO - GLib Input, Output and Streaming Library
3 * Copyright © 2008 Christian Kellner, Samuel Cormier-Iijima
4 * © 2008 codethink
5 * Copyright © 2009 Red Hat, Inc
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General
18 * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
20 * Authors: Christian Kellner <gicmo@gnome.org>
21 * Samuel Cormier-Iijima <sciyoshi@gmail.com>
22 * Ryan Lortie <desrt@desrt.ca>
23 * Alexander Larsson <alexl@redhat.com>
26 #include "config.h"
28 #include "gsocketconnection.h"
30 #include "gsocketoutputstream.h"
31 #include "gsocketinputstream.h"
32 #include "gioprivate.h"
33 #include <gio/giostream.h>
34 #include <gio/gtask.h>
35 #include "gunixconnection.h"
36 #include "gtcpconnection.h"
37 #include "glibintl.h"
40 /**
41 * SECTION:gsocketconnection
42 * @short_description: A socket connection
43 * @include: gio/gio.h
44 * @see_also: #GIOStream, #GSocketClient, #GSocketListener
46 * #GSocketConnection is a #GIOStream for a connected socket. They
47 * can be created either by #GSocketClient when connecting to a host,
48 * or by #GSocketListener when accepting a new client.
50 * The type of the #GSocketConnection object returned from these calls
51 * depends on the type of the underlying socket that is in use. For
52 * instance, for a TCP/IP connection it will be a #GTcpConnection.
54 * Choosing what type of object to construct is done with the socket
55 * connection factory, and it is possible for 3rd parties to register
56 * custom socket connection types for specific combination of socket
57 * family/type/protocol using g_socket_connection_factory_register_type().
59 * To close a #GSocketConnection, use g_io_stream_close(). Closing both
60 * substreams of the #GIOStream separately will not close the underlying
61 * #GSocket.
63 * Since: 2.22
66 enum
68 PROP_NONE,
69 PROP_SOCKET,
72 struct _GSocketConnectionPrivate
74 GSocket *socket;
75 GInputStream *input_stream;
76 GOutputStream *output_stream;
78 GSocketAddress *cached_remote_address;
80 gboolean in_dispose;
83 static gboolean g_socket_connection_close (GIOStream *stream,
84 GCancellable *cancellable,
85 GError **error);
86 static void g_socket_connection_close_async (GIOStream *stream,
87 int io_priority,
88 GCancellable *cancellable,
89 GAsyncReadyCallback callback,
90 gpointer user_data);
91 static gboolean g_socket_connection_close_finish (GIOStream *stream,
92 GAsyncResult *result,
93 GError **error);
95 G_DEFINE_TYPE_WITH_PRIVATE (GSocketConnection, g_socket_connection, G_TYPE_IO_STREAM)
97 static GInputStream *
98 g_socket_connection_get_input_stream (GIOStream *io_stream)
100 GSocketConnection *connection = G_SOCKET_CONNECTION (io_stream);
102 if (connection->priv->input_stream == NULL)
103 connection->priv->input_stream = (GInputStream *)
104 _g_socket_input_stream_new (connection->priv->socket);
106 return connection->priv->input_stream;
109 static GOutputStream *
110 g_socket_connection_get_output_stream (GIOStream *io_stream)
112 GSocketConnection *connection = G_SOCKET_CONNECTION (io_stream);
114 if (connection->priv->output_stream == NULL)
115 connection->priv->output_stream = (GOutputStream *)
116 _g_socket_output_stream_new (connection->priv->socket);
118 return connection->priv->output_stream;
122 * g_socket_connection_is_connected:
123 * @connection: a #GSocketConnection
125 * Checks if @connection is connected. This is equivalent to calling
126 * g_socket_is_connected() on @connection's underlying #GSocket.
128 * Returns: whether @connection is connected
130 * Since: 2.32
132 gboolean
133 g_socket_connection_is_connected (GSocketConnection *connection)
135 return g_socket_is_connected (connection->priv->socket);
139 * g_socket_connection_connect:
140 * @connection: a #GSocketConnection
141 * @address: a #GSocketAddress specifying the remote address.
142 * @cancellable: (allow-none): a %GCancellable or %NULL
143 * @error: #GError for error reporting, or %NULL to ignore.
145 * Connect @connection to the specified remote address.
147 * Returns: %TRUE if the connection succeeded, %FALSE on error
149 * Since: 2.32
151 gboolean
152 g_socket_connection_connect (GSocketConnection *connection,
153 GSocketAddress *address,
154 GCancellable *cancellable,
155 GError **error)
157 g_return_val_if_fail (G_IS_SOCKET_CONNECTION (connection), FALSE);
158 g_return_val_if_fail (G_IS_SOCKET_ADDRESS (address), FALSE);
160 return g_socket_connect (connection->priv->socket, address,
161 cancellable, error);
164 static gboolean g_socket_connection_connect_callback (GSocket *socket,
165 GIOCondition condition,
166 gpointer user_data);
169 * g_socket_connection_connect_async:
170 * @connection: a #GSocketConnection
171 * @address: a #GSocketAddress specifying the remote address.
172 * @cancellable: (allow-none): a %GCancellable or %NULL
173 * @callback: (scope async): a #GAsyncReadyCallback
174 * @user_data: (closure): user data for the callback
176 * Asynchronously connect @connection to the specified remote address.
178 * This clears the #GSocket:blocking flag on @connection's underlying
179 * socket if it is currently set.
181 * Use g_socket_connection_connect_finish() to retrieve the result.
183 * Since: 2.32
185 void
186 g_socket_connection_connect_async (GSocketConnection *connection,
187 GSocketAddress *address,
188 GCancellable *cancellable,
189 GAsyncReadyCallback callback,
190 gpointer user_data)
192 GTask *task;
193 GError *tmp_error = NULL;
195 g_return_if_fail (G_IS_SOCKET_CONNECTION (connection));
196 g_return_if_fail (G_IS_SOCKET_ADDRESS (address));
198 task = g_task_new (connection, cancellable, callback, user_data);
200 g_socket_set_blocking (connection->priv->socket, FALSE);
202 if (g_socket_connect (connection->priv->socket, address,
203 cancellable, &tmp_error))
205 g_task_return_boolean (task, TRUE);
206 g_object_unref (task);
208 else if (g_error_matches (tmp_error, G_IO_ERROR, G_IO_ERROR_PENDING))
210 GSource *source;
212 g_error_free (tmp_error);
213 source = g_socket_create_source (connection->priv->socket,
214 G_IO_OUT, cancellable);
215 g_task_attach_source (task, source,
216 (GSourceFunc) g_socket_connection_connect_callback);
217 g_source_unref (source);
219 else
221 g_task_return_error (task, tmp_error);
222 g_object_unref (task);
226 static gboolean
227 g_socket_connection_connect_callback (GSocket *socket,
228 GIOCondition condition,
229 gpointer user_data)
231 GTask *task = user_data;
232 GSocketConnection *connection = g_task_get_source_object (task);
233 GError *error = NULL;
235 if (g_socket_check_connect_result (connection->priv->socket, &error))
236 g_task_return_boolean (task, TRUE);
237 else
238 g_task_return_error (task, error);
240 g_object_unref (task);
241 return FALSE;
245 * g_socket_connection_connect_finish:
246 * @connection: a #GSocketConnection
247 * @result: the #GAsyncResult
248 * @error: #GError for error reporting, or %NULL to ignore.
250 * Gets the result of a g_socket_connection_connect_async() call.
252 * Returns: %TRUE if the connection succeeded, %FALSE on error
254 * Since: 2.32
256 gboolean
257 g_socket_connection_connect_finish (GSocketConnection *connection,
258 GAsyncResult *result,
259 GError **error)
261 g_return_val_if_fail (G_IS_SOCKET_CONNECTION (connection), FALSE);
262 g_return_val_if_fail (g_task_is_valid (result, connection), FALSE);
264 return g_task_propagate_boolean (G_TASK (result), error);
268 * g_socket_connection_get_socket:
269 * @connection: a #GSocketConnection
271 * Gets the underlying #GSocket object of the connection.
272 * This can be useful if you want to do something unusual on it
273 * not supported by the #GSocketConnection APIs.
275 * Returns: (transfer none): a #GSocket or %NULL on error.
277 * Since: 2.22
279 GSocket *
280 g_socket_connection_get_socket (GSocketConnection *connection)
282 g_return_val_if_fail (G_IS_SOCKET_CONNECTION (connection), NULL);
284 return connection->priv->socket;
288 * g_socket_connection_get_local_address:
289 * @connection: a #GSocketConnection
290 * @error: #GError for error reporting, or %NULL to ignore.
292 * Try to get the local address of a socket connection.
294 * Returns: (transfer full): a #GSocketAddress or %NULL on error.
295 * Free the returned object with g_object_unref().
297 * Since: 2.22
299 GSocketAddress *
300 g_socket_connection_get_local_address (GSocketConnection *connection,
301 GError **error)
303 return g_socket_get_local_address (connection->priv->socket, error);
307 * g_socket_connection_get_remote_address:
308 * @connection: a #GSocketConnection
309 * @error: #GError for error reporting, or %NULL to ignore.
311 * Try to get the remote address of a socket connection.
313 * Since GLib 2.40, when used with g_socket_client_connect() or
314 * g_socket_client_connect_async(), during emission of
315 * %G_SOCKET_CLIENT_CONNECTING, this function will return the remote
316 * address that will be used for the connection. This allows
317 * applications to print e.g. "Connecting to example.com
318 * (10.42.77.3)...".
320 * Returns: (transfer full): a #GSocketAddress or %NULL on error.
321 * Free the returned object with g_object_unref().
323 * Since: 2.22
325 GSocketAddress *
326 g_socket_connection_get_remote_address (GSocketConnection *connection,
327 GError **error)
329 if (!g_socket_is_connected (connection->priv->socket))
331 return connection->priv->cached_remote_address ?
332 g_object_ref (connection->priv->cached_remote_address) : NULL;
334 return g_socket_get_remote_address (connection->priv->socket, error);
337 /* Private API allowing applications to retrieve the resolved address
338 * now, before we start connecting.
340 * https://bugzilla.gnome.org/show_bug.cgi?id=712547
342 void
343 g_socket_connection_set_cached_remote_address (GSocketConnection *connection,
344 GSocketAddress *address)
346 g_clear_object (&connection->priv->cached_remote_address);
347 connection->priv->cached_remote_address = address ? g_object_ref (address) : NULL;
350 static void
351 g_socket_connection_get_property (GObject *object,
352 guint prop_id,
353 GValue *value,
354 GParamSpec *pspec)
356 GSocketConnection *connection = G_SOCKET_CONNECTION (object);
358 switch (prop_id)
360 case PROP_SOCKET:
361 g_value_set_object (value, connection->priv->socket);
362 break;
364 default:
365 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
369 static void
370 g_socket_connection_set_property (GObject *object,
371 guint prop_id,
372 const GValue *value,
373 GParamSpec *pspec)
375 GSocketConnection *connection = G_SOCKET_CONNECTION (object);
377 switch (prop_id)
379 case PROP_SOCKET:
380 connection->priv->socket = G_SOCKET (g_value_dup_object (value));
381 break;
383 default:
384 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
388 static void
389 g_socket_connection_constructed (GObject *object)
391 GSocketConnection *connection = G_SOCKET_CONNECTION (object);
393 g_assert (connection->priv->socket != NULL);
396 static void
397 g_socket_connection_dispose (GObject *object)
399 GSocketConnection *connection = G_SOCKET_CONNECTION (object);
401 connection->priv->in_dispose = TRUE;
403 g_clear_object (&connection->priv->cached_remote_address);
405 G_OBJECT_CLASS (g_socket_connection_parent_class)
406 ->dispose (object);
408 connection->priv->in_dispose = FALSE;
411 static void
412 g_socket_connection_finalize (GObject *object)
414 GSocketConnection *connection = G_SOCKET_CONNECTION (object);
416 if (connection->priv->input_stream)
417 g_object_unref (connection->priv->input_stream);
419 if (connection->priv->output_stream)
420 g_object_unref (connection->priv->output_stream);
422 g_object_unref (connection->priv->socket);
424 G_OBJECT_CLASS (g_socket_connection_parent_class)
425 ->finalize (object);
428 static void
429 g_socket_connection_class_init (GSocketConnectionClass *klass)
431 GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
432 GIOStreamClass *stream_class = G_IO_STREAM_CLASS (klass);
434 gobject_class->set_property = g_socket_connection_set_property;
435 gobject_class->get_property = g_socket_connection_get_property;
436 gobject_class->constructed = g_socket_connection_constructed;
437 gobject_class->finalize = g_socket_connection_finalize;
438 gobject_class->dispose = g_socket_connection_dispose;
440 stream_class->get_input_stream = g_socket_connection_get_input_stream;
441 stream_class->get_output_stream = g_socket_connection_get_output_stream;
442 stream_class->close_fn = g_socket_connection_close;
443 stream_class->close_async = g_socket_connection_close_async;
444 stream_class->close_finish = g_socket_connection_close_finish;
446 g_object_class_install_property (gobject_class,
447 PROP_SOCKET,
448 g_param_spec_object ("socket",
449 P_("Socket"),
450 P_("The underlying GSocket"),
451 G_TYPE_SOCKET,
452 G_PARAM_CONSTRUCT_ONLY |
453 G_PARAM_READWRITE |
454 G_PARAM_STATIC_STRINGS));
457 static void
458 g_socket_connection_init (GSocketConnection *connection)
460 connection->priv = g_socket_connection_get_instance_private (connection);
463 static gboolean
464 g_socket_connection_close (GIOStream *stream,
465 GCancellable *cancellable,
466 GError **error)
468 GSocketConnection *connection = G_SOCKET_CONNECTION (stream);
470 if (connection->priv->output_stream)
471 g_output_stream_close (connection->priv->output_stream,
472 cancellable, NULL);
473 if (connection->priv->input_stream)
474 g_input_stream_close (connection->priv->input_stream,
475 cancellable, NULL);
477 /* Don't close the underlying socket if this is being called
478 * as part of dispose(); when destroying the GSocketConnection,
479 * we only want to close the socket if we're holding the last
480 * reference on it, and in that case it will close itself when
481 * we unref it in finalize().
483 if (connection->priv->in_dispose)
484 return TRUE;
486 return g_socket_close (connection->priv->socket, error);
490 static void
491 g_socket_connection_close_async (GIOStream *stream,
492 int io_priority,
493 GCancellable *cancellable,
494 GAsyncReadyCallback callback,
495 gpointer user_data)
497 GTask *task;
498 GIOStreamClass *class;
499 GError *error;
501 class = G_IO_STREAM_GET_CLASS (stream);
503 task = g_task_new (stream, cancellable, callback, user_data);
505 /* socket close is not blocked, just do it! */
506 error = NULL;
507 if (class->close_fn &&
508 !class->close_fn (stream, cancellable, &error))
509 g_task_return_error (task, error);
510 else
511 g_task_return_boolean (task, TRUE);
513 g_object_unref (task);
516 static gboolean
517 g_socket_connection_close_finish (GIOStream *stream,
518 GAsyncResult *result,
519 GError **error)
521 return g_task_propagate_boolean (G_TASK (result), error);
524 typedef struct {
525 GSocketFamily socket_family;
526 GSocketType socket_type;
527 int protocol;
528 GType implementation;
529 } ConnectionFactory;
531 static guint
532 connection_factory_hash (gconstpointer key)
534 const ConnectionFactory *factory = key;
535 guint h;
537 h = factory->socket_family ^ (factory->socket_type << 4) ^ (factory->protocol << 8);
538 /* This is likely to be small, so spread over whole
539 hash space to get some distribution */
540 h = h ^ (h << 8) ^ (h << 16) ^ (h << 24);
542 return h;
545 static gboolean
546 connection_factory_equal (gconstpointer _a,
547 gconstpointer _b)
549 const ConnectionFactory *a = _a;
550 const ConnectionFactory *b = _b;
552 if (a->socket_family != b->socket_family)
553 return FALSE;
555 if (a->socket_type != b->socket_type)
556 return FALSE;
558 if (a->protocol != b->protocol)
559 return FALSE;
561 return TRUE;
564 static GHashTable *connection_factories = NULL;
565 G_LOCK_DEFINE_STATIC(connection_factories);
568 * g_socket_connection_factory_register_type:
569 * @g_type: a #GType, inheriting from %G_TYPE_SOCKET_CONNECTION
570 * @family: a #GSocketFamily
571 * @type: a #GSocketType
572 * @protocol: a protocol id
574 * Looks up the #GType to be used when creating socket connections on
575 * sockets with the specified @family, @type and @protocol.
577 * If no type is registered, the #GSocketConnection base type is returned.
579 * Since: 2.22
581 void
582 g_socket_connection_factory_register_type (GType g_type,
583 GSocketFamily family,
584 GSocketType type,
585 gint protocol)
587 ConnectionFactory *factory;
589 g_return_if_fail (g_type_is_a (g_type, G_TYPE_SOCKET_CONNECTION));
591 G_LOCK (connection_factories);
593 if (connection_factories == NULL)
594 connection_factories = g_hash_table_new_full (connection_factory_hash,
595 connection_factory_equal,
596 (GDestroyNotify)g_free,
597 NULL);
599 factory = g_new0 (ConnectionFactory, 1);
600 factory->socket_family = family;
601 factory->socket_type = type;
602 factory->protocol = protocol;
603 factory->implementation = g_type;
605 g_hash_table_insert (connection_factories,
606 factory, factory);
608 G_UNLOCK (connection_factories);
611 static void
612 init_builtin_types (void)
614 #ifndef G_OS_WIN32
615 g_type_ensure (G_TYPE_UNIX_CONNECTION);
616 #endif
617 g_type_ensure (G_TYPE_TCP_CONNECTION);
621 * g_socket_connection_factory_lookup_type:
622 * @family: a #GSocketFamily
623 * @type: a #GSocketType
624 * @protocol_id: a protocol id
626 * Looks up the #GType to be used when creating socket connections on
627 * sockets with the specified @family, @type and @protocol_id.
629 * If no type is registered, the #GSocketConnection base type is returned.
631 * Returns: a #GType
633 * Since: 2.22
635 GType
636 g_socket_connection_factory_lookup_type (GSocketFamily family,
637 GSocketType type,
638 gint protocol_id)
640 ConnectionFactory *factory, key;
641 GType g_type;
643 init_builtin_types ();
645 G_LOCK (connection_factories);
647 g_type = G_TYPE_SOCKET_CONNECTION;
649 if (connection_factories)
651 key.socket_family = family;
652 key.socket_type = type;
653 key.protocol = protocol_id;
655 factory = g_hash_table_lookup (connection_factories, &key);
656 if (factory)
657 g_type = factory->implementation;
660 G_UNLOCK (connection_factories);
662 return g_type;
666 * g_socket_connection_factory_create_connection:
667 * @socket: a #GSocket
669 * Creates a #GSocketConnection subclass of the right type for
670 * @socket.
672 * Returns: (transfer full): a #GSocketConnection
674 * Since: 2.22
676 GSocketConnection *
677 g_socket_connection_factory_create_connection (GSocket *socket)
679 GType type;
681 type = g_socket_connection_factory_lookup_type (g_socket_get_family (socket),
682 g_socket_get_socket_type (socket),
683 g_socket_get_protocol (socket));
684 return g_object_new (type, "socket", socket, NULL);