1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
3 * soup-socket.c: Socket networking code.
5 * Copyright (C) 2000-2003, Ximian, Inc.
19 #include "soup-socket.h"
20 #include "soup-address.h"
21 #include "soup-filter-input-stream.h"
22 #include "soup-marshal.h"
23 #include "soup-misc.h"
24 #include "soup-misc-private.h"
28 * @short_description: A network socket
30 * #SoupSocket is libsoup's TCP socket type. While it is primarily
31 * intended for internal use, #SoupSocket<!-- -->s are exposed in the
32 * API in various places, and some of their methods (eg,
33 * soup_socket_get_remote_address()) may be useful to applications.
36 G_DEFINE_TYPE (SoupSocket, soup_socket, G_TYPE_OBJECT)
47 static guint signals[LAST_SIGNAL] = { 0 };
60 PROP_USE_THREAD_CONTEXT,
62 PROP_TRUSTED_CERTIFICATE,
71 SoupAddress *local_addr, *remote_addr;
74 GInputStream *istream;
75 GOutputStream *ostream;
76 GTlsCertificateFlags tls_errors;
83 guint clean_dispose:1;
84 guint use_thread_context:1;
87 GMainContext *async_context;
89 GSource *read_src, *write_src;
91 GMutex iolock, addrlock;
94 GCancellable *connect_cancel;
96 #define SOUP_SOCKET_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), SOUP_TYPE_SOCKET, SoupSocketPrivate))
98 static void set_property (GObject *object, guint prop_id,
99 const GValue *value, GParamSpec *pspec);
100 static void get_property (GObject *object, guint prop_id,
101 GValue *value, GParamSpec *pspec);
103 static void soup_socket_peer_certificate_changed (GObject *conn,
108 soup_socket_init (SoupSocket *sock)
110 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
112 priv->non_blocking = TRUE;
113 g_mutex_init (&priv->addrlock);
114 g_mutex_init (&priv->iolock);
118 disconnect_internal (SoupSocket *sock, gboolean close)
120 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
124 g_socket_close (priv->gsock, NULL);
125 g_object_unref (priv->gsock);
129 if (G_IS_TLS_CONNECTION (priv->conn))
130 g_signal_handlers_disconnect_by_func (priv->conn, soup_socket_peer_certificate_changed, sock);
131 g_clear_object (&priv->conn);
134 if (priv->read_src) {
135 g_source_destroy (priv->read_src);
136 priv->read_src = NULL;
138 if (priv->write_src) {
139 g_source_destroy (priv->write_src);
140 priv->write_src = NULL;
145 finalize (GObject *object)
147 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (object);
149 if (priv->connect_cancel) {
150 if (priv->clean_dispose)
151 g_warning ("Disposing socket %p during connect", object);
152 g_object_unref (priv->connect_cancel);
155 if (priv->clean_dispose)
156 g_warning ("Disposing socket %p while still connected", object);
157 disconnect_internal (SOUP_SOCKET (object), TRUE);
160 g_clear_object (&priv->istream);
161 g_clear_object (&priv->ostream);
163 if (priv->local_addr)
164 g_object_unref (priv->local_addr);
165 if (priv->remote_addr)
166 g_object_unref (priv->remote_addr);
168 if (priv->watch_src) {
169 if (priv->clean_dispose && !priv->is_server)
170 g_warning ("Disposing socket %p during async op", object);
171 g_source_destroy (priv->watch_src);
173 if (priv->async_context)
174 g_main_context_unref (priv->async_context);
176 g_mutex_clear (&priv->addrlock);
177 g_mutex_clear (&priv->iolock);
179 G_OBJECT_CLASS (soup_socket_parent_class)->finalize (object);
183 soup_socket_class_init (SoupSocketClass *socket_class)
185 GObjectClass *object_class = G_OBJECT_CLASS (socket_class);
187 g_type_class_add_private (socket_class, sizeof (SoupSocketPrivate));
189 /* virtual method override */
190 object_class->finalize = finalize;
191 object_class->set_property = set_property;
192 object_class->get_property = get_property;
197 * SoupSocket::readable:
200 * Emitted when an async socket is readable. See
201 * soup_socket_read(), soup_socket_read_until() and
202 * #SoupSocket:non-blocking.
205 g_signal_new ("readable",
206 G_OBJECT_CLASS_TYPE (object_class),
208 G_STRUCT_OFFSET (SoupSocketClass, readable),
210 _soup_marshal_NONE__NONE,
214 * SoupSocket::writable:
217 * Emitted when an async socket is writable. See
218 * soup_socket_write() and #SoupSocket:non-blocking.
221 g_signal_new ("writable",
222 G_OBJECT_CLASS_TYPE (object_class),
224 G_STRUCT_OFFSET (SoupSocketClass, writable),
226 _soup_marshal_NONE__NONE,
230 * SoupSocket::disconnected:
233 * Emitted when the socket is disconnected, for whatever
236 signals[DISCONNECTED] =
237 g_signal_new ("disconnected",
238 G_OBJECT_CLASS_TYPE (object_class),
240 G_STRUCT_OFFSET (SoupSocketClass, disconnected),
242 _soup_marshal_NONE__NONE,
246 * SoupSocket::new-connection:
248 * @new: the new socket
250 * Emitted when a listening socket (set up with
251 * soup_socket_listen()) receives a new connection.
253 * You must ref the @new if you want to keep it; otherwise it
254 * will be destroyed after the signal is emitted.
256 signals[NEW_CONNECTION] =
257 g_signal_new ("new_connection",
258 G_OBJECT_CLASS_TYPE (object_class),
260 G_STRUCT_OFFSET (SoupSocketClass, new_connection),
262 _soup_marshal_NONE__OBJECT,
268 * @event: the event that occurred
269 * @connection: the current connection state
271 * Emitted when a network-related event occurs. See
272 * #GSocketClient::event for more details.
277 g_signal_new ("event",
278 G_OBJECT_CLASS_TYPE (object_class),
284 G_TYPE_SOCKET_CLIENT_EVENT,
290 * SOUP_SOCKET_LOCAL_ADDRESS:
292 * Alias for the #SoupSocket:local-address property. (Address
293 * of local end of socket.)
295 g_object_class_install_property (
296 object_class, PROP_LOCAL_ADDRESS,
297 g_param_spec_object (SOUP_SOCKET_LOCAL_ADDRESS,
299 "Address of local end of socket",
301 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
303 * SOUP_SOCKET_REMOTE_ADDRESS:
305 * Alias for the #SoupSocket:remote-address property. (Address
306 * of remote end of socket.)
308 g_object_class_install_property (
309 object_class, PROP_REMOTE_ADDRESS,
310 g_param_spec_object (SOUP_SOCKET_REMOTE_ADDRESS,
312 "Address of remote end of socket",
314 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
316 * SoupSocket:non-blocking:
318 * Whether or not the socket uses non-blocking I/O.
320 * #SoupSocket's I/O methods are designed around the idea of
321 * using a single codepath for both synchronous and
322 * asynchronous I/O. If you want to read off a #SoupSocket,
323 * the "correct" way to do it is to call soup_socket_read() or
324 * soup_socket_read_until() repeatedly until you have read
325 * everything you want. If it returns %SOUP_SOCKET_WOULD_BLOCK
326 * at any point, stop reading and wait for it to emit the
327 * #SoupSocket::readable signal. Then go back to the
328 * reading-as-much-as-you-can loop. Likewise, for writing to a
329 * #SoupSocket, you should call soup_socket_write() either
330 * until you have written everything, or it returns
331 * %SOUP_SOCKET_WOULD_BLOCK (in which case you wait for
332 * #SoupSocket::writable and then go back into the loop).
334 * Code written this way will work correctly with both
335 * blocking and non-blocking sockets; blocking sockets will
336 * simply never return %SOUP_SOCKET_WOULD_BLOCK, and so the
337 * code that handles that case just won't get used for them.
340 * SOUP_SOCKET_FLAG_NONBLOCKING:
342 * Alias for the #SoupSocket:non-blocking property. (Whether
343 * or not the socket uses non-blocking I/O.)
345 g_object_class_install_property (
346 object_class, PROP_NON_BLOCKING,
347 g_param_spec_boolean (SOUP_SOCKET_FLAG_NONBLOCKING,
349 "Whether or not the socket uses non-blocking I/O",
353 * SOUP_SOCKET_IS_SERVER:
355 * Alias for the #SoupSocket:is-server property. (Whether or
356 * not the socket is a server socket.)
358 g_object_class_install_property (
359 object_class, PROP_IS_SERVER,
360 g_param_spec_boolean (SOUP_SOCKET_IS_SERVER,
362 "Whether or not the socket is a server socket",
366 * SOUP_SOCKET_SSL_CREDENTIALS:
368 * Alias for the #SoupSocket:ssl-creds property.
369 * (SSL credential information.)
371 /* For historical reasons, there's only a single property
372 * here, which is a GTlsDatabase for client sockets, and
373 * a GTlsCertificate for server sockets. Whee!
375 g_object_class_install_property (
376 object_class, PROP_SSL_CREDENTIALS,
377 g_param_spec_pointer (SOUP_SOCKET_SSL_CREDENTIALS,
379 "SSL credential information, passed from the session to the SSL implementation",
382 * SOUP_SOCKET_SSL_STRICT:
384 * Alias for the #SoupSocket:ssl-strict property.
386 g_object_class_install_property (
387 object_class, PROP_SSL_STRICT,
388 g_param_spec_boolean (SOUP_SOCKET_SSL_STRICT,
389 "Strictly validate SSL certificates",
390 "Whether certificate errors should be considered a connection error",
392 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
394 * SOUP_SOCKET_SSL_FALLBACK:
396 * Alias for the #SoupSocket:ssl-fallback property.
398 g_object_class_install_property (
399 object_class, PROP_SSL_FALLBACK,
400 g_param_spec_boolean (SOUP_SOCKET_SSL_FALLBACK,
402 "Use SSLv3 instead of TLS (client-side only)",
404 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
406 * SOUP_SOCKET_TRUSTED_CERTIFICATE:
408 * Alias for the #SoupSocket:trusted-certificate
411 g_object_class_install_property (
412 object_class, PROP_TRUSTED_CERTIFICATE,
413 g_param_spec_boolean (SOUP_SOCKET_TRUSTED_CERTIFICATE,
414 "Trusted Certificate",
415 "Whether the server certificate is trusted, if this is an SSL socket",
419 * SOUP_SOCKET_ASYNC_CONTEXT:
421 * Alias for the #SoupSocket:async-context property. (The
422 * socket's #GMainContext.)
424 g_object_class_install_property (
425 object_class, PROP_ASYNC_CONTEXT,
426 g_param_spec_pointer (SOUP_SOCKET_ASYNC_CONTEXT,
427 "Async GMainContext",
428 "The GMainContext to dispatch this socket's async I/O in",
429 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
432 * SOUP_SOCKET_USE_THREAD_CONTEXT:
434 * Alias for the #SoupSocket:use-thread-context property. (Use
435 * g_main_context_get_thread_default())
440 * SoupSocket:use-thread-context:
442 * Use g_main_context_get_thread_default().
446 g_object_class_install_property (
447 object_class, PROP_USE_THREAD_CONTEXT,
448 g_param_spec_boolean (SOUP_SOCKET_USE_THREAD_CONTEXT,
449 "Use thread context",
450 "Use g_main_context_get_thread_default",
452 G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
455 * SOUP_SOCKET_TIMEOUT:
457 * Alias for the #SoupSocket:timeout property. (The timeout
458 * in seconds for blocking socket I/O operations.)
460 g_object_class_install_property (
461 object_class, PROP_TIMEOUT,
462 g_param_spec_uint (SOUP_SOCKET_TIMEOUT,
464 "Value in seconds to timeout a blocking I/O",
468 g_object_class_install_property (
469 object_class, PROP_CLEAN_DISPOSE,
470 g_param_spec_boolean ("clean-dispose",
472 "Warn on unclean dispose",
474 G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY));
476 * SOUP_SOCKET_TLS_CERTIFICATE:
478 * Alias for the #SoupSocket:tls-certificate
479 * property. Note that this property's value is only useful
480 * if the socket is for a TLS connection, and only reliable
481 * after some data has been transferred to or from it.
485 g_object_class_install_property (
486 object_class, PROP_TLS_CERTIFICATE,
487 g_param_spec_object (SOUP_SOCKET_TLS_CERTIFICATE,
489 "The peer's TLS certificate",
490 G_TYPE_TLS_CERTIFICATE,
493 * SOUP_SOCKET_TLS_ERRORS:
495 * Alias for the #SoupSocket:tls-errors
496 * property. Note that this property's value is only useful
497 * if the socket is for a TLS connection, and only reliable
498 * after some data has been transferred to or from it.
502 g_object_class_install_property (
503 object_class, PROP_TLS_ERRORS,
504 g_param_spec_flags (SOUP_SOCKET_TLS_ERRORS,
506 "Errors with the peer's TLS certificate",
507 G_TYPE_TLS_CERTIFICATE_FLAGS, 0,
513 finish_socket_setup (SoupSocketPrivate *priv)
519 priv->conn = (GIOStream *)g_socket_connection_factory_create_connection (priv->gsock);
521 priv->istream = soup_filter_input_stream_new (g_io_stream_get_input_stream (priv->conn));
523 priv->ostream = g_object_ref (g_io_stream_get_output_stream (priv->conn));
525 g_socket_set_timeout (priv->gsock, priv->timeout);
529 set_property (GObject *object, guint prop_id,
530 const GValue *value, GParamSpec *pspec)
532 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (object);
535 case PROP_LOCAL_ADDRESS:
536 priv->local_addr = (SoupAddress *)g_value_dup_object (value);
538 case PROP_REMOTE_ADDRESS:
539 priv->remote_addr = (SoupAddress *)g_value_dup_object (value);
541 case PROP_NON_BLOCKING:
542 priv->non_blocking = g_value_get_boolean (value);
544 case PROP_SSL_CREDENTIALS:
545 priv->ssl_creds = g_value_get_pointer (value);
547 case PROP_SSL_STRICT:
548 priv->ssl_strict = g_value_get_boolean (value);
550 case PROP_SSL_FALLBACK:
551 priv->ssl_fallback = g_value_get_boolean (value);
553 case PROP_ASYNC_CONTEXT:
554 priv->async_context = g_value_get_pointer (value);
555 if (priv->async_context)
556 g_main_context_ref (priv->async_context);
558 case PROP_USE_THREAD_CONTEXT:
559 priv->use_thread_context = g_value_get_boolean (value);
562 priv->timeout = g_value_get_uint (value);
564 g_socket_set_timeout (priv->gsock, priv->timeout);
566 case PROP_CLEAN_DISPOSE:
567 priv->clean_dispose = g_value_get_boolean (value);
570 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
576 get_property (GObject *object, guint prop_id,
577 GValue *value, GParamSpec *pspec)
579 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (object);
582 case PROP_LOCAL_ADDRESS:
583 g_value_set_object (value, soup_socket_get_local_address (SOUP_SOCKET (object)));
585 case PROP_REMOTE_ADDRESS:
586 g_value_set_object (value, soup_socket_get_remote_address (SOUP_SOCKET (object)));
588 case PROP_NON_BLOCKING:
589 g_value_set_boolean (value, priv->non_blocking);
592 g_value_set_boolean (value, priv->is_server);
594 case PROP_SSL_CREDENTIALS:
595 g_value_set_pointer (value, priv->ssl_creds);
597 case PROP_SSL_STRICT:
598 g_value_set_boolean (value, priv->ssl_strict);
600 case PROP_SSL_FALLBACK:
601 g_value_set_boolean (value, priv->ssl_fallback);
603 case PROP_TRUSTED_CERTIFICATE:
604 g_value_set_boolean (value, priv->tls_errors == 0);
606 case PROP_ASYNC_CONTEXT:
607 g_value_set_pointer (value, priv->async_context ? g_main_context_ref (priv->async_context) : NULL);
609 case PROP_USE_THREAD_CONTEXT:
610 g_value_set_boolean (value, priv->use_thread_context);
613 g_value_set_uint (value, priv->timeout);
615 case PROP_TLS_CERTIFICATE:
616 if (G_IS_TLS_CONNECTION (priv->conn))
617 g_value_set_object (value, g_tls_connection_get_peer_certificate (G_TLS_CONNECTION (priv->conn)));
619 g_value_set_object (value, NULL);
621 case PROP_TLS_ERRORS:
622 g_value_set_flags (value, priv->tls_errors);
625 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
633 * @optname1: name of first property to set (or %NULL)
634 * @...: value of @optname1, followed by additional property/value pairs
636 * Creates a new (disconnected) socket
638 * Return value: the new socket
641 soup_socket_new (const char *optname1, ...)
646 va_start (ap, optname1);
647 sock = (SoupSocket *)g_object_new_valist (SOUP_TYPE_SOCKET,
655 proxy_socket_client_event (GSocketClient *client,
656 GSocketClientEvent event,
657 GSocketConnectable *connectable,
658 GIOStream *connection,
661 SoupSocket *sock = user_data;
663 g_signal_emit (sock, signals[EVENT], 0,
668 socket_connected (SoupSocket *sock, GSocketConnection *conn, GError *error)
670 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
672 if (priv->connect_cancel) {
673 GCancellable *cancellable = priv->connect_cancel;
675 g_object_unref (priv->connect_cancel);
676 priv->connect_cancel = NULL;
677 if (g_cancellable_is_cancelled (cancellable))
678 return SOUP_STATUS_CANCELLED;
682 if (error->domain == G_RESOLVER_ERROR) {
683 g_error_free (error);
684 return SOUP_STATUS_CANT_RESOLVE;
686 g_error_free (error);
687 return SOUP_STATUS_CANT_CONNECT;
691 priv->conn = (GIOStream *)conn;
692 priv->gsock = g_object_ref (g_socket_connection_get_socket (conn));
693 finish_socket_setup (priv);
695 return SOUP_STATUS_OK;
699 * SoupSocketCallback:
700 * @sock: the #SoupSocket
701 * @status: an HTTP status code indicating success or failure
702 * @user_data: the data passed to soup_socket_connect_async()
704 * The callback function passed to soup_socket_connect_async().
709 SoupSocketCallback callback;
711 } SoupSocketAsyncConnectData;
714 async_connected (GObject *client, GAsyncResult *result, gpointer data)
716 SoupSocketAsyncConnectData *sacd = data;
717 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sacd->sock);
718 GError *error = NULL;
719 GSocketConnection *conn;
722 if (priv->async_context && !priv->use_thread_context)
723 g_main_context_pop_thread_default (priv->async_context);
725 conn = g_socket_client_connect_finish (G_SOCKET_CLIENT (client),
727 status = socket_connected (sacd->sock, conn, error);
729 sacd->callback (sacd->sock, status, sacd->user_data);
730 g_object_unref (sacd->sock);
731 g_slice_free (SoupSocketAsyncConnectData, sacd);
735 * soup_socket_connect_async:
736 * @sock: a client #SoupSocket (which must not already be connected)
737 * @cancellable: a #GCancellable, or %NULL
738 * @callback: (scope async): callback to call after connecting
739 * @user_data: data to pass to @callback
741 * Begins asynchronously connecting to @sock's remote address. The
742 * socket will call @callback when it succeeds or fails (but not
743 * before returning from this function).
745 * If @cancellable is non-%NULL, it can be used to cancel the
746 * connection. @callback will still be invoked in this case, with a
747 * status of %SOUP_STATUS_CANCELLED.
750 soup_socket_connect_async (SoupSocket *sock, GCancellable *cancellable,
751 SoupSocketCallback callback, gpointer user_data)
753 SoupSocketPrivate *priv;
754 SoupSocketAsyncConnectData *sacd;
755 GSocketClient *client;
757 g_return_if_fail (SOUP_IS_SOCKET (sock));
758 priv = SOUP_SOCKET_GET_PRIVATE (sock);
759 g_return_if_fail (priv->remote_addr != NULL);
761 sacd = g_slice_new0 (SoupSocketAsyncConnectData);
762 sacd->sock = g_object_ref (sock);
763 sacd->callback = callback;
764 sacd->user_data = user_data;
766 priv->connect_cancel = cancellable ? g_object_ref (cancellable) : g_cancellable_new ();
768 if (priv->async_context && !priv->use_thread_context)
769 g_main_context_push_thread_default (priv->async_context);
771 client = g_socket_client_new ();
772 g_signal_connect (client, "event",
773 G_CALLBACK (proxy_socket_client_event), sock);
775 g_socket_client_set_timeout (client, priv->timeout);
776 g_socket_client_connect_async (client,
777 G_SOCKET_CONNECTABLE (priv->remote_addr),
778 priv->connect_cancel,
779 async_connected, sacd);
780 g_object_unref (client);
784 * soup_socket_connect_sync:
785 * @sock: a client #SoupSocket (which must not already be connected)
786 * @cancellable: a #GCancellable, or %NULL
788 * Attempt to synchronously connect @sock to its remote address.
790 * If @cancellable is non-%NULL, it can be used to cancel the
791 * connection, in which case soup_socket_connect_sync() will return
792 * %SOUP_STATUS_CANCELLED.
794 * Return value: a success or failure code.
797 soup_socket_connect_sync (SoupSocket *sock, GCancellable *cancellable)
799 SoupSocketPrivate *priv;
800 GSocketClient *client;
801 GSocketConnection *conn;
802 GError *error = NULL;
804 g_return_val_if_fail (SOUP_IS_SOCKET (sock), SOUP_STATUS_MALFORMED);
805 priv = SOUP_SOCKET_GET_PRIVATE (sock);
806 g_return_val_if_fail (!priv->is_server, SOUP_STATUS_MALFORMED);
807 g_return_val_if_fail (priv->gsock == NULL, SOUP_STATUS_MALFORMED);
808 g_return_val_if_fail (priv->remote_addr != NULL, SOUP_STATUS_MALFORMED);
811 g_object_ref (cancellable);
813 cancellable = g_cancellable_new ();
814 priv->connect_cancel = cancellable;
816 client = g_socket_client_new ();
817 g_signal_connect (client, "event",
818 G_CALLBACK (proxy_socket_client_event), sock);
820 g_socket_client_set_timeout (client, priv->timeout);
821 conn = g_socket_client_connect (client,
822 G_SOCKET_CONNECTABLE (priv->remote_addr),
823 priv->connect_cancel, &error);
824 g_object_unref (client);
826 return socket_connected (sock, conn, error);
830 soup_socket_get_fd (SoupSocket *sock)
832 g_return_val_if_fail (SOUP_IS_SOCKET (sock), -1);
834 return g_socket_get_fd (SOUP_SOCKET_GET_PRIVATE (sock)->gsock);
838 soup_socket_get_gsocket (SoupSocket *sock)
840 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
842 return SOUP_SOCKET_GET_PRIVATE (sock)->gsock;
846 soup_socket_get_iostream (SoupSocket *sock)
848 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
850 return SOUP_SOCKET_GET_PRIVATE (sock)->conn;
854 soup_socket_create_watch (SoupSocketPrivate *priv, GIOCondition cond,
855 GPollableSourceFunc callback, gpointer user_data,
856 GCancellable *cancellable)
859 GMainContext *async_context;
862 watch = g_pollable_input_stream_create_source (G_POLLABLE_INPUT_STREAM (priv->istream), cancellable);
864 watch = g_pollable_output_stream_create_source (G_POLLABLE_OUTPUT_STREAM (priv->ostream), cancellable);
865 g_source_set_callback (watch, (GSourceFunc)callback, user_data, NULL);
867 if (priv->use_thread_context)
868 async_context = g_main_context_get_thread_default ();
870 async_context = priv->async_context;
872 g_source_attach (watch, async_context);
873 g_source_unref (watch);
879 listen_watch (GObject *pollable, gpointer data)
881 SoupSocket *sock = data, *new;
882 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock), *new_priv;
885 new_gsock = g_socket_accept (priv->gsock, NULL, NULL);
889 new = g_object_new (SOUP_TYPE_SOCKET, NULL);
890 new_priv = SOUP_SOCKET_GET_PRIVATE (new);
891 new_priv->gsock = new_gsock;
892 if (priv->async_context)
893 new_priv->async_context = g_main_context_ref (priv->async_context);
894 new_priv->use_thread_context = priv->use_thread_context;
895 new_priv->non_blocking = priv->non_blocking;
896 new_priv->is_server = TRUE;
897 new_priv->ssl = priv->ssl;
899 new_priv->ssl_creds = priv->ssl_creds;
900 finish_socket_setup (new_priv);
902 if (new_priv->ssl_creds) {
903 if (!soup_socket_start_proxy_ssl (new, NULL, NULL)) {
904 g_object_unref (new);
909 g_signal_emit (sock, signals[NEW_CONNECTION], 0, new);
910 g_object_unref (new);
916 * soup_socket_listen:
917 * @sock: a server #SoupSocket (which must not already be connected or
920 * Makes @sock start listening on its local address. When connections
921 * come in, @sock will emit #SoupSocket::new_connection.
923 * Return value: whether or not @sock is now listening.
926 soup_socket_listen (SoupSocket *sock)
929 SoupSocketPrivate *priv;
930 GSocketAddress *addr;
932 g_return_val_if_fail (SOUP_IS_SOCKET (sock), FALSE);
933 priv = SOUP_SOCKET_GET_PRIVATE (sock);
934 g_return_val_if_fail (priv->gsock == NULL, FALSE);
935 g_return_val_if_fail (priv->local_addr != NULL, FALSE);
937 priv->is_server = TRUE;
939 /* @local_addr may have its port set to 0. So we intentionally
940 * don't store it in priv->local_addr, so that if the
941 * caller calls soup_socket_get_local_address() later, we'll
942 * have to make a new addr by calling getsockname(), which
943 * will have the right port number.
945 addr = soup_address_get_gsockaddr (priv->local_addr);
946 g_return_val_if_fail (addr != NULL, FALSE);
948 priv->gsock = g_socket_new (g_socket_address_get_family (addr),
949 G_SOCKET_TYPE_STREAM,
950 G_SOCKET_PROTOCOL_DEFAULT,
954 finish_socket_setup (priv);
957 if (!g_socket_bind (priv->gsock, addr, TRUE, NULL))
959 /* Force local_addr to be re-resolved now */
960 g_object_unref (priv->local_addr);
961 priv->local_addr = NULL;
964 if (!g_socket_listen (priv->gsock, NULL))
967 priv->watch_src = soup_socket_create_watch (priv, G_IO_IN,
970 g_object_unref (addr);
975 disconnect_internal (sock, TRUE);
976 g_object_unref (addr);
982 soup_socket_peer_certificate_changed (GObject *conn, GParamSpec *pspec,
985 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
987 priv->tls_errors = g_tls_connection_get_peer_certificate_errors (G_TLS_CONNECTION (priv->conn));
989 g_object_notify (sock, "tls-certificate");
990 g_object_notify (sock, "tls-errors");
994 soup_socket_accept_certificate (GTlsConnection *conn, GTlsCertificate *cert,
995 GTlsCertificateFlags errors, gpointer sock)
1001 * soup_socket_start_ssl:
1003 * @cancellable: a #GCancellable
1005 * Starts using SSL on @socket.
1007 * Return value: success or failure
1010 soup_socket_start_ssl (SoupSocket *sock, GCancellable *cancellable)
1012 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1014 return soup_socket_start_proxy_ssl (sock, soup_address_get_name (priv->remote_addr), cancellable);
1018 * soup_socket_start_proxy_ssl:
1020 * @ssl_host: hostname of the SSL server
1021 * @cancellable: a #GCancellable
1023 * Starts using SSL on @socket, expecting to find a host named
1026 * Return value: success or failure
1029 soup_socket_start_proxy_ssl (SoupSocket *sock, const char *ssl_host,
1030 GCancellable *cancellable)
1032 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1033 GTlsBackend *backend = g_tls_backend_get_default ();
1035 if (G_IS_TLS_CONNECTION (priv->conn))
1038 if (g_cancellable_is_cancelled (cancellable))
1043 if (!priv->is_server) {
1044 GTlsClientConnection *conn;
1045 GSocketConnectable *identity;
1047 identity = g_network_address_new (ssl_host, 0);
1048 conn = g_initable_new (g_tls_backend_get_client_connection_type (backend),
1050 "base-io-stream", priv->conn,
1051 "server-identity", identity,
1052 "database", priv->ssl_creds,
1053 "require-close-notify", FALSE,
1054 "use-ssl3", priv->ssl_fallback,
1056 g_object_unref (identity);
1061 g_object_unref (priv->conn);
1062 priv->conn = G_IO_STREAM (conn);
1064 if (!priv->ssl_strict) {
1065 g_signal_connect (conn, "accept-certificate",
1066 G_CALLBACK (soup_socket_accept_certificate),
1070 GTlsServerConnection *conn;
1072 conn = g_initable_new (g_tls_backend_get_server_connection_type (backend),
1074 "base-io-stream", priv->conn,
1075 "certificate", priv->ssl_creds,
1076 "use-system-certdb", FALSE,
1077 "require-close-notify", FALSE,
1082 g_object_unref (priv->conn);
1083 priv->conn = G_IO_STREAM (conn);
1086 g_signal_connect (priv->conn, "notify::peer-certificate",
1087 G_CALLBACK (soup_socket_peer_certificate_changed), sock);
1090 g_object_unref (priv->istream);
1092 g_object_unref (priv->ostream);
1094 priv->istream = soup_filter_input_stream_new (g_io_stream_get_input_stream (priv->conn));
1095 priv->ostream = g_object_ref (g_io_stream_get_output_stream (priv->conn));
1100 soup_socket_handshake_sync (SoupSocket *sock,
1101 GCancellable *cancellable)
1103 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1104 GError *error = NULL;
1107 if (g_tls_connection_handshake (G_TLS_CONNECTION (priv->conn),
1108 cancellable, &error))
1109 return SOUP_STATUS_OK;
1110 else if (!priv->ssl_fallback &&
1111 g_error_matches (error, G_TLS_ERROR, G_TLS_ERROR_NOT_TLS)) {
1112 g_error_free (error);
1113 return SOUP_STATUS_TLS_FAILED;
1115 g_error_free (error);
1116 return SOUP_STATUS_SSL_FAILED;
1121 handshake_async_ready (GObject *source, GAsyncResult *result, gpointer user_data)
1123 SoupSocketAsyncConnectData *data = user_data;
1124 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (data->sock);
1125 GError *error = NULL;
1128 if (priv->async_context && !priv->use_thread_context)
1129 g_main_context_pop_thread_default (priv->async_context);
1131 if (g_tls_connection_handshake_finish (G_TLS_CONNECTION (source),
1133 status = SOUP_STATUS_OK;
1134 else if (!priv->ssl_fallback &&
1135 g_error_matches (error, G_TLS_ERROR, G_TLS_ERROR_NOT_TLS))
1136 status = SOUP_STATUS_TLS_FAILED;
1138 status = SOUP_STATUS_SSL_FAILED;
1139 g_clear_error (&error);
1141 data->callback (data->sock, status, data->user_data);
1142 g_object_unref (data->sock);
1143 g_slice_free (SoupSocketAsyncConnectData, data);
1147 soup_socket_handshake_async (SoupSocket *sock,
1148 GCancellable *cancellable,
1149 SoupSocketCallback callback,
1152 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1153 SoupSocketAsyncConnectData *data;
1157 data = g_slice_new (SoupSocketAsyncConnectData);
1158 data->sock = g_object_ref (sock);
1159 data->callback = callback;
1160 data->user_data = user_data;
1162 if (priv->async_context && !priv->use_thread_context)
1163 g_main_context_push_thread_default (priv->async_context);
1164 g_tls_connection_handshake_async (G_TLS_CONNECTION (priv->conn),
1166 cancellable, handshake_async_ready,
1171 * soup_socket_is_ssl:
1172 * @sock: a #SoupSocket
1174 * Tests if @sock is doing (or has attempted to do) SSL.
1176 * Return value: %TRUE if @sock has SSL credentials set
1179 soup_socket_is_ssl (SoupSocket *sock)
1181 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1187 * soup_socket_disconnect:
1188 * @sock: a #SoupSocket
1190 * Disconnects @sock. Any further read or write attempts on it will
1194 soup_socket_disconnect (SoupSocket *sock)
1196 SoupSocketPrivate *priv;
1197 gboolean already_disconnected = FALSE;
1199 g_return_if_fail (SOUP_IS_SOCKET (sock));
1200 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1202 if (priv->connect_cancel) {
1203 disconnect_internal (sock, FALSE);
1204 g_cancellable_cancel (priv->connect_cancel);
1206 } else if (g_mutex_trylock (&priv->iolock)) {
1208 disconnect_internal (sock, TRUE);
1210 already_disconnected = TRUE;
1211 g_mutex_unlock (&priv->iolock);
1213 /* Another thread is currently doing IO, so
1214 * we can't close the socket. So just shutdown
1215 * the file descriptor to force the I/O to fail.
1216 * (It will actually be closed when the socket
1219 g_socket_shutdown (priv->gsock, TRUE, TRUE, NULL);
1222 if (already_disconnected)
1225 /* Keep ref around signals in case the object is unreferenced
1228 g_object_ref (sock);
1230 /* Give all readers a chance to notice the connection close */
1231 g_signal_emit (sock, signals[READABLE], 0);
1233 /* FIXME: can't disconnect until all data is read */
1235 /* Then let everyone know we're disconnected */
1236 g_signal_emit (sock, signals[DISCONNECTED], 0);
1238 g_object_unref (sock);
1242 * soup_socket_is_connected:
1243 * @sock: a #SoupSocket
1245 * Tests if @sock is connected to another host
1247 * Return value: %TRUE or %FALSE.
1250 soup_socket_is_connected (SoupSocket *sock)
1252 SoupSocketPrivate *priv;
1254 g_return_val_if_fail (SOUP_IS_SOCKET (sock), FALSE);
1255 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1257 return priv->conn != NULL;
1261 * soup_socket_get_local_address:
1262 * @sock: a #SoupSocket
1264 * Returns the #SoupAddress corresponding to the local end of @sock.
1266 * Return value: (transfer none): the #SoupAddress
1269 soup_socket_get_local_address (SoupSocket *sock)
1271 SoupSocketPrivate *priv;
1273 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
1274 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1276 g_mutex_lock (&priv->addrlock);
1277 if (!priv->local_addr) {
1278 GSocketAddress *addr;
1279 struct sockaddr_storage sa;
1282 addr = g_socket_get_local_address (priv->gsock, NULL);
1283 sa_len = g_socket_address_get_native_size (addr);
1284 g_socket_address_to_native (addr, &sa, sa_len, NULL);
1285 priv->local_addr = soup_address_new_from_sockaddr ((struct sockaddr *)&sa, sa_len);
1286 g_object_unref (addr);
1288 g_mutex_unlock (&priv->addrlock);
1290 return priv->local_addr;
1294 * soup_socket_get_remote_address:
1295 * @sock: a #SoupSocket
1297 * Returns the #SoupAddress corresponding to the remote end of @sock.
1299 * Return value: (transfer none): the #SoupAddress
1302 soup_socket_get_remote_address (SoupSocket *sock)
1304 SoupSocketPrivate *priv;
1306 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
1307 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1309 g_mutex_lock (&priv->addrlock);
1310 if (!priv->remote_addr) {
1311 GSocketAddress *addr;
1312 struct sockaddr_storage sa;
1315 addr = g_socket_get_remote_address (priv->gsock, NULL);
1316 sa_len = g_socket_address_get_native_size (addr);
1317 g_socket_address_to_native (addr, &sa, sa_len, NULL);
1318 priv->remote_addr = soup_address_new_from_sockaddr ((struct sockaddr *)&sa, sa_len);
1319 g_object_unref (addr);
1321 g_mutex_unlock (&priv->addrlock);
1323 return priv->remote_addr;
1327 soup_socket_get_input_stream (SoupSocket *sock)
1329 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
1331 return SOUP_SOCKET_GET_PRIVATE (sock)->istream;
1335 soup_socket_get_output_stream (SoupSocket *sock)
1337 g_return_val_if_fail (SOUP_IS_SOCKET (sock), NULL);
1339 return SOUP_SOCKET_GET_PRIVATE (sock)->ostream;
1344 socket_read_watch (GObject *pollable, gpointer user_data)
1346 SoupSocket *sock = user_data;
1347 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1349 priv->read_src = NULL;
1350 g_signal_emit (sock, signals[READABLE], 0);
1354 static SoupSocketIOStatus
1355 translate_read_status (SoupSocket *sock, GCancellable *cancellable,
1356 gssize my_nread, gsize *nread,
1357 GError *my_err, GError **error)
1359 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1362 g_assert_no_error (my_err);
1364 return SOUP_SOCKET_OK;
1365 } else if (my_nread == 0) {
1366 g_assert_no_error (my_err);
1368 return SOUP_SOCKET_EOF;
1369 } else if (g_error_matches (my_err, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK)) {
1370 g_clear_error (&my_err);
1371 if (!priv->read_src) {
1373 soup_socket_create_watch (priv, G_IO_IN,
1374 socket_read_watch, sock,
1377 return SOUP_SOCKET_WOULD_BLOCK;
1380 g_propagate_error (error, my_err);
1381 return SOUP_SOCKET_ERROR;
1385 * SoupSocketIOStatus:
1386 * @SOUP_SOCKET_OK: Success
1387 * @SOUP_SOCKET_WOULD_BLOCK: Cannot read/write any more at this time
1388 * @SOUP_SOCKET_EOF: End of file
1389 * @SOUP_SOCKET_ERROR: Other error
1391 * Return value from the #SoupSocket IO methods.
1397 * @buffer: buffer to read into
1398 * @len: size of @buffer in bytes
1399 * @nread: (out): on return, the number of bytes read into @buffer
1400 * @cancellable: a #GCancellable, or %NULL
1401 * @error: error pointer
1403 * Attempts to read up to @len bytes from @sock into @buffer. If some
1404 * data is successfully read, soup_socket_read() will return
1405 * %SOUP_SOCKET_OK, and *@nread will contain the number of bytes
1406 * actually read (which may be less than @len).
1408 * If @sock is non-blocking, and no data is available, the return
1409 * value will be %SOUP_SOCKET_WOULD_BLOCK. In this case, the caller
1410 * can connect to the #SoupSocket::readable signal to know when there
1411 * is more data to read. (NB: You MUST read all available data off the
1412 * socket first. #SoupSocket::readable is only emitted after
1413 * soup_socket_read() returns %SOUP_SOCKET_WOULD_BLOCK, and it is only
1414 * emitted once. See the documentation for #SoupSocket:non-blocking.)
1416 * Return value: a #SoupSocketIOStatus, as described above (or
1417 * %SOUP_SOCKET_EOF if the socket is no longer connected, or
1418 * %SOUP_SOCKET_ERROR on any other error, in which case @error will
1422 soup_socket_read (SoupSocket *sock, gpointer buffer, gsize len,
1423 gsize *nread, GCancellable *cancellable, GError **error)
1425 SoupSocketPrivate *priv;
1426 SoupSocketIOStatus status;
1428 GError *my_err = NULL;
1430 g_return_val_if_fail (SOUP_IS_SOCKET (sock), SOUP_SOCKET_ERROR);
1431 g_return_val_if_fail (nread != NULL, SOUP_SOCKET_ERROR);
1433 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1435 g_mutex_lock (&priv->iolock);
1437 if (!priv->istream) {
1438 status = SOUP_SOCKET_EOF;
1442 if (!priv->non_blocking) {
1443 my_nread = g_input_stream_read (priv->istream, buffer, len,
1444 cancellable, &my_err);
1446 my_nread = g_pollable_input_stream_read_nonblocking (G_POLLABLE_INPUT_STREAM (priv->istream),
1448 cancellable, &my_err);
1450 status = translate_read_status (sock, cancellable,
1451 my_nread, nread, my_err, error);
1454 g_mutex_unlock (&priv->iolock);
1460 * soup_socket_read_until:
1462 * @buffer: buffer to read into
1463 * @len: size of @buffer in bytes
1464 * @boundary: boundary to read until
1465 * @boundary_len: length of @boundary in bytes
1466 * @nread: (out): on return, the number of bytes read into @buffer
1467 * @got_boundary: on return, whether or not the data in @buffer
1468 * ends with the boundary string
1469 * @cancellable: a #GCancellable, or %NULL
1470 * @error: error pointer
1472 * Like soup_socket_read(), but reads no further than the first
1473 * occurrence of @boundary. (If the boundary is found, it will be
1474 * included in the returned data, and *@got_boundary will be set to
1475 * %TRUE.) Any data after the boundary will returned in future reads.
1477 * soup_socket_read_until() will almost always return fewer than @len
1478 * bytes: if the boundary is found, then it will only return the bytes
1479 * up until the end of the boundary, and if the boundary is not found,
1480 * then it will leave the last <literal>(boundary_len - 1)</literal>
1481 * bytes in its internal buffer, in case they form the start of the
1482 * boundary string. Thus, @len normally needs to be at least 1 byte
1483 * longer than @boundary_len if you want to make any progress at all.
1485 * Return value: as for soup_socket_read()
1488 soup_socket_read_until (SoupSocket *sock, gpointer buffer, gsize len,
1489 gconstpointer boundary, gsize boundary_len,
1490 gsize *nread, gboolean *got_boundary,
1491 GCancellable *cancellable, GError **error)
1493 SoupSocketPrivate *priv;
1494 SoupSocketIOStatus status;
1496 GError *my_err = NULL;
1498 g_return_val_if_fail (SOUP_IS_SOCKET (sock), SOUP_SOCKET_ERROR);
1499 g_return_val_if_fail (nread != NULL, SOUP_SOCKET_ERROR);
1500 g_return_val_if_fail (len >= boundary_len, SOUP_SOCKET_ERROR);
1502 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1504 g_mutex_lock (&priv->iolock);
1506 *got_boundary = FALSE;
1509 status = SOUP_SOCKET_EOF;
1511 my_nread = soup_filter_input_stream_read_until (
1512 SOUP_FILTER_INPUT_STREAM (priv->istream),
1513 buffer, len, boundary, boundary_len,
1514 !priv->non_blocking,
1515 got_boundary, cancellable, &my_err);
1516 status = translate_read_status (sock, cancellable,
1517 my_nread, nread, my_err, error);
1520 g_mutex_unlock (&priv->iolock);
1525 socket_write_watch (GObject *pollable, gpointer user_data)
1527 SoupSocket *sock = user_data;
1528 SoupSocketPrivate *priv = SOUP_SOCKET_GET_PRIVATE (sock);
1530 priv->write_src = NULL;
1531 g_signal_emit (sock, signals[WRITABLE], 0);
1536 * soup_socket_write:
1538 * @buffer: data to write
1539 * @len: size of @buffer, in bytes
1540 * @nwrote: (out): on return, number of bytes written
1541 * @cancellable: a #GCancellable, or %NULL
1542 * @error: error pointer
1544 * Attempts to write @len bytes from @buffer to @sock. If some data is
1545 * successfully written, the return status will be %SOUP_SOCKET_OK,
1546 * and *@nwrote will contain the number of bytes actually written
1547 * (which may be less than @len).
1549 * If @sock is non-blocking, and no data could be written right away,
1550 * the return value will be %SOUP_SOCKET_WOULD_BLOCK. In this case,
1551 * the caller can connect to the #SoupSocket::writable signal to know
1552 * when more data can be written. (NB: #SoupSocket::writable is only
1553 * emitted after soup_socket_write() returns %SOUP_SOCKET_WOULD_BLOCK,
1554 * and it is only emitted once. See the documentation for
1555 * #SoupSocket:non-blocking.)
1557 * Return value: a #SoupSocketIOStatus, as described above (or
1558 * %SOUP_SOCKET_EOF or %SOUP_SOCKET_ERROR. @error will be set if the
1559 * return value is %SOUP_SOCKET_ERROR.)
1562 soup_socket_write (SoupSocket *sock, gconstpointer buffer,
1563 gsize len, gsize *nwrote,
1564 GCancellable *cancellable, GError **error)
1566 SoupSocketPrivate *priv;
1567 GError *my_err = NULL;
1570 g_return_val_if_fail (SOUP_IS_SOCKET (sock), SOUP_SOCKET_ERROR);
1571 g_return_val_if_fail (nwrote != NULL, SOUP_SOCKET_ERROR);
1573 priv = SOUP_SOCKET_GET_PRIVATE (sock);
1575 g_mutex_lock (&priv->iolock);
1578 g_mutex_unlock (&priv->iolock);
1579 return SOUP_SOCKET_EOF;
1581 if (priv->write_src) {
1582 g_mutex_unlock (&priv->iolock);
1583 return SOUP_SOCKET_WOULD_BLOCK;
1586 if (!priv->non_blocking) {
1587 my_nwrote = g_output_stream_write (priv->ostream,
1589 cancellable, &my_err);
1591 my_nwrote = g_pollable_output_stream_write_nonblocking (
1592 G_POLLABLE_OUTPUT_STREAM (priv->ostream),
1593 buffer, len, cancellable, &my_err);
1596 if (my_nwrote > 0) {
1597 g_mutex_unlock (&priv->iolock);
1598 g_clear_error (&my_err);
1599 *nwrote = my_nwrote;
1600 return SOUP_SOCKET_OK;
1603 if (g_error_matches (my_err, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK)) {
1604 g_mutex_unlock (&priv->iolock);
1605 g_clear_error (&my_err);
1608 soup_socket_create_watch (priv,
1610 socket_write_watch, sock, cancellable);
1611 return SOUP_SOCKET_WOULD_BLOCK;
1614 g_mutex_unlock (&priv->iolock);
1615 g_propagate_error (error, my_err);
1616 return SOUP_SOCKET_ERROR;