1 /* GIO - GLib Input, Output and Streaming Library
3 * Copyright © 2008, 2009 codethink
4 * Copyright © 2009 Red Hat, Inc
5 * Copyright © 2018 Igalia S.L.
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.1 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: Ryan Lortie <desrt@desrt.ca>
21 * Alexander Larsson <alexl@redhat.com>
25 #include "gsocketclient.h"
30 #include <gio/gioenumtypes.h>
31 #include <gio/gsocketaddressenumerator.h>
32 #include <gio/gsocketconnectable.h>
33 #include <gio/gsocketconnection.h>
34 #include <gio/gioprivate.h>
35 #include <gio/gproxyaddressenumerator.h>
36 #include <gio/gproxyaddress.h>
37 #include <gio/gtask.h>
38 #include <gio/gcancellable.h>
39 #include <gio/gioerror.h>
40 #include <gio/gsocket.h>
41 #include <gio/gnetworkaddress.h>
42 #include <gio/gnetworkservice.h>
43 #include <gio/gproxy.h>
44 #include <gio/gproxyresolver.h>
45 #include <gio/gsocketaddress.h>
46 #include <gio/gtcpconnection.h>
47 #include <gio/gtcpwrapperconnection.h>
48 #include <gio/gtlscertificate.h>
49 #include <gio/gtlsclientconnection.h>
50 #include <gio/ginetaddress.h>
53 /* As recommended by RFC 8305 this is the time it waits
54 * on a connection before starting another concurrent attempt.
56 #define HAPPY_EYEBALLS_CONNECTION_ATTEMPT_TIMEOUT_MS 250
59 * SECTION:gsocketclient
60 * @short_description: Helper for connecting to a network service
62 * @see_also: #GSocketConnection, #GSocketListener
64 * #GSocketClient is a lightweight high-level utility class for connecting to
65 * a network host using a connection oriented socket type.
67 * You create a #GSocketClient object, set any options you want, and then
68 * call a sync or async connect operation, which returns a #GSocketConnection
69 * subclass on success.
71 * The type of the #GSocketConnection object returned depends on the type of
72 * the underlying socket that is in use. For instance, for a TCP/IP connection
73 * it will be a #GTcpConnection.
75 * As #GSocketClient is a lightweight object, you don't need to cache it. You
76 * can just create a new one any time you need one.
88 static guint signals[LAST_SIGNAL] = { 0 };
100 PROP_TLS_VALIDATION_FLAGS,
104 struct _GSocketClientPrivate
106 GSocketFamily family;
108 GSocketProtocol protocol;
109 GSocketAddress *local_address;
111 gboolean enable_proxy;
112 GHashTable *app_proxies;
114 GTlsCertificateFlags tls_validation_flags;
115 GProxyResolver *proxy_resolver;
118 G_DEFINE_TYPE_WITH_PRIVATE (GSocketClient, g_socket_client, G_TYPE_OBJECT)
121 create_socket (GSocketClient *client,
122 GSocketAddress *dest_address,
125 GSocketFamily family;
128 family = client->priv->family;
129 if (family == G_SOCKET_FAMILY_INVALID &&
130 client->priv->local_address != NULL)
131 family = g_socket_address_get_family (client->priv->local_address);
132 if (family == G_SOCKET_FAMILY_INVALID)
133 family = g_socket_address_get_family (dest_address);
135 socket = g_socket_new (family,
137 client->priv->protocol,
142 if (client->priv->local_address)
144 if (!g_socket_bind (socket,
145 client->priv->local_address,
149 g_object_unref (socket);
154 if (client->priv->timeout)
155 g_socket_set_timeout (socket, client->priv->timeout);
161 can_use_proxy (GSocketClient *client)
163 GSocketClientPrivate *priv = client->priv;
165 return priv->enable_proxy
166 && priv->type == G_SOCKET_TYPE_STREAM;
170 clarify_connect_error (GError *error,
171 GSocketConnectable *connectable,
172 GSocketAddress *address)
175 char *tmp_name = NULL;
177 if (G_IS_PROXY_ADDRESS (address))
179 name = tmp_name = g_inet_address_to_string (g_inet_socket_address_get_address (G_INET_SOCKET_ADDRESS (address)));
181 g_prefix_error (&error, _("Could not connect to proxy server %s: "), name);
185 if (G_IS_NETWORK_ADDRESS (connectable))
186 name = g_network_address_get_hostname (G_NETWORK_ADDRESS (connectable));
187 else if (G_IS_NETWORK_SERVICE (connectable))
188 name = g_network_service_get_domain (G_NETWORK_SERVICE (connectable));
189 else if (G_IS_INET_SOCKET_ADDRESS (connectable))
190 name = tmp_name = g_inet_address_to_string (g_inet_socket_address_get_address (G_INET_SOCKET_ADDRESS (connectable)));
195 g_prefix_error (&error, _("Could not connect to %s: "), name);
197 g_prefix_error (&error, _("Could not connect: "));
204 g_socket_client_init (GSocketClient *client)
206 client->priv = g_socket_client_get_instance_private (client);
207 client->priv->type = G_SOCKET_TYPE_STREAM;
208 client->priv->app_proxies = g_hash_table_new_full (g_str_hash,
215 * g_socket_client_new:
217 * Creates a new #GSocketClient with the default options.
219 * Returns: a #GSocketClient.
220 * Free the returned object with g_object_unref().
225 g_socket_client_new (void)
227 return g_object_new (G_TYPE_SOCKET_CLIENT, NULL);
231 g_socket_client_finalize (GObject *object)
233 GSocketClient *client = G_SOCKET_CLIENT (object);
235 g_clear_object (&client->priv->local_address);
236 g_clear_object (&client->priv->proxy_resolver);
238 G_OBJECT_CLASS (g_socket_client_parent_class)->finalize (object);
240 g_hash_table_unref (client->priv->app_proxies);
244 g_socket_client_get_property (GObject *object,
249 GSocketClient *client = G_SOCKET_CLIENT (object);
254 g_value_set_enum (value, client->priv->family);
258 g_value_set_enum (value, client->priv->type);
262 g_value_set_enum (value, client->priv->protocol);
265 case PROP_LOCAL_ADDRESS:
266 g_value_set_object (value, client->priv->local_address);
270 g_value_set_uint (value, client->priv->timeout);
273 case PROP_ENABLE_PROXY:
274 g_value_set_boolean (value, client->priv->enable_proxy);
278 g_value_set_boolean (value, g_socket_client_get_tls (client));
281 case PROP_TLS_VALIDATION_FLAGS:
282 g_value_set_flags (value, g_socket_client_get_tls_validation_flags (client));
285 case PROP_PROXY_RESOLVER:
286 g_value_set_object (value, g_socket_client_get_proxy_resolver (client));
290 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
295 g_socket_client_set_property (GObject *object,
300 GSocketClient *client = G_SOCKET_CLIENT (object);
305 g_socket_client_set_family (client, g_value_get_enum (value));
309 g_socket_client_set_socket_type (client, g_value_get_enum (value));
313 g_socket_client_set_protocol (client, g_value_get_enum (value));
316 case PROP_LOCAL_ADDRESS:
317 g_socket_client_set_local_address (client, g_value_get_object (value));
321 g_socket_client_set_timeout (client, g_value_get_uint (value));
324 case PROP_ENABLE_PROXY:
325 g_socket_client_set_enable_proxy (client, g_value_get_boolean (value));
329 g_socket_client_set_tls (client, g_value_get_boolean (value));
332 case PROP_TLS_VALIDATION_FLAGS:
333 g_socket_client_set_tls_validation_flags (client, g_value_get_flags (value));
336 case PROP_PROXY_RESOLVER:
337 g_socket_client_set_proxy_resolver (client, g_value_get_object (value));
341 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
346 * g_socket_client_get_family:
347 * @client: a #GSocketClient.
349 * Gets the socket family of the socket client.
351 * See g_socket_client_set_family() for details.
353 * Returns: a #GSocketFamily
358 g_socket_client_get_family (GSocketClient *client)
360 return client->priv->family;
364 * g_socket_client_set_family:
365 * @client: a #GSocketClient.
366 * @family: a #GSocketFamily
368 * Sets the socket family of the socket client.
369 * If this is set to something other than %G_SOCKET_FAMILY_INVALID
370 * then the sockets created by this object will be of the specified
373 * This might be useful for instance if you want to force the local
374 * connection to be an ipv4 socket, even though the address might
375 * be an ipv6 mapped to ipv4 address.
380 g_socket_client_set_family (GSocketClient *client,
381 GSocketFamily family)
383 if (client->priv->family == family)
386 client->priv->family = family;
387 g_object_notify (G_OBJECT (client), "family");
391 * g_socket_client_get_socket_type:
392 * @client: a #GSocketClient.
394 * Gets the socket type of the socket client.
396 * See g_socket_client_set_socket_type() for details.
398 * Returns: a #GSocketFamily
403 g_socket_client_get_socket_type (GSocketClient *client)
405 return client->priv->type;
409 * g_socket_client_set_socket_type:
410 * @client: a #GSocketClient.
411 * @type: a #GSocketType
413 * Sets the socket type of the socket client.
414 * The sockets created by this object will be of the specified
417 * It doesn't make sense to specify a type of %G_SOCKET_TYPE_DATAGRAM,
418 * as GSocketClient is used for connection oriented services.
423 g_socket_client_set_socket_type (GSocketClient *client,
426 if (client->priv->type == type)
429 client->priv->type = type;
430 g_object_notify (G_OBJECT (client), "type");
434 * g_socket_client_get_protocol:
435 * @client: a #GSocketClient
437 * Gets the protocol name type of the socket client.
439 * See g_socket_client_set_protocol() for details.
441 * Returns: a #GSocketProtocol
446 g_socket_client_get_protocol (GSocketClient *client)
448 return client->priv->protocol;
452 * g_socket_client_set_protocol:
453 * @client: a #GSocketClient.
454 * @protocol: a #GSocketProtocol
456 * Sets the protocol of the socket client.
457 * The sockets created by this object will use of the specified
460 * If @protocol is %0 that means to use the default
461 * protocol for the socket family and type.
466 g_socket_client_set_protocol (GSocketClient *client,
467 GSocketProtocol protocol)
469 if (client->priv->protocol == protocol)
472 client->priv->protocol = protocol;
473 g_object_notify (G_OBJECT (client), "protocol");
477 * g_socket_client_get_local_address:
478 * @client: a #GSocketClient.
480 * Gets the local address of the socket client.
482 * See g_socket_client_set_local_address() for details.
484 * Returns: (transfer none): a #GSocketAddress or %NULL. Do not free.
489 g_socket_client_get_local_address (GSocketClient *client)
491 return client->priv->local_address;
495 * g_socket_client_set_local_address:
496 * @client: a #GSocketClient.
497 * @address: (nullable): a #GSocketAddress, or %NULL
499 * Sets the local address of the socket client.
500 * The sockets created by this object will bound to the
501 * specified address (if not %NULL) before connecting.
503 * This is useful if you want to ensure that the local
504 * side of the connection is on a specific port, or on
505 * a specific interface.
510 g_socket_client_set_local_address (GSocketClient *client,
511 GSocketAddress *address)
514 g_object_ref (address);
516 if (client->priv->local_address)
518 g_object_unref (client->priv->local_address);
520 client->priv->local_address = address;
521 g_object_notify (G_OBJECT (client), "local-address");
525 * g_socket_client_get_timeout:
526 * @client: a #GSocketClient
528 * Gets the I/O timeout time for sockets created by @client.
530 * See g_socket_client_set_timeout() for details.
532 * Returns: the timeout in seconds
537 g_socket_client_get_timeout (GSocketClient *client)
539 return client->priv->timeout;
544 * g_socket_client_set_timeout:
545 * @client: a #GSocketClient.
546 * @timeout: the timeout
548 * Sets the I/O timeout for sockets created by @client. @timeout is a
549 * time in seconds, or 0 for no timeout (the default).
551 * The timeout value affects the initial connection attempt as well,
552 * so setting this may cause calls to g_socket_client_connect(), etc,
553 * to fail with %G_IO_ERROR_TIMED_OUT.
558 g_socket_client_set_timeout (GSocketClient *client,
561 if (client->priv->timeout == timeout)
564 client->priv->timeout = timeout;
565 g_object_notify (G_OBJECT (client), "timeout");
569 * g_socket_client_get_enable_proxy:
570 * @client: a #GSocketClient.
572 * Gets the proxy enable state; see g_socket_client_set_enable_proxy()
574 * Returns: whether proxying is enabled
579 g_socket_client_get_enable_proxy (GSocketClient *client)
581 return client->priv->enable_proxy;
585 * g_socket_client_set_enable_proxy:
586 * @client: a #GSocketClient.
587 * @enable: whether to enable proxies
589 * Sets whether or not @client attempts to make connections via a
590 * proxy server. When enabled (the default), #GSocketClient will use a
591 * #GProxyResolver to determine if a proxy protocol such as SOCKS is
592 * needed, and automatically do the necessary proxy negotiation.
594 * See also g_socket_client_set_proxy_resolver().
599 g_socket_client_set_enable_proxy (GSocketClient *client,
603 if (client->priv->enable_proxy == enable)
606 client->priv->enable_proxy = enable;
607 g_object_notify (G_OBJECT (client), "enable-proxy");
611 * g_socket_client_get_tls:
612 * @client: a #GSocketClient.
614 * Gets whether @client creates TLS connections. See
615 * g_socket_client_set_tls() for details.
617 * Returns: whether @client uses TLS
622 g_socket_client_get_tls (GSocketClient *client)
624 return client->priv->tls;
628 * g_socket_client_set_tls:
629 * @client: a #GSocketClient.
630 * @tls: whether to use TLS
632 * Sets whether @client creates TLS (aka SSL) connections. If @tls is
633 * %TRUE, @client will wrap its connections in a #GTlsClientConnection
634 * and perform a TLS handshake when connecting.
636 * Note that since #GSocketClient must return a #GSocketConnection,
637 * but #GTlsClientConnection is not a #GSocketConnection, this
638 * actually wraps the resulting #GTlsClientConnection in a
639 * #GTcpWrapperConnection when returning it. You can use
640 * g_tcp_wrapper_connection_get_base_io_stream() on the return value
641 * to extract the #GTlsClientConnection.
643 * If you need to modify the behavior of the TLS handshake (eg, by
644 * setting a client-side certificate to use, or connecting to the
645 * #GTlsConnection::accept-certificate signal), you can connect to
646 * @client's #GSocketClient::event signal and wait for it to be
647 * emitted with %G_SOCKET_CLIENT_TLS_HANDSHAKING, which will give you
648 * a chance to see the #GTlsClientConnection before the handshake
654 g_socket_client_set_tls (GSocketClient *client,
658 if (tls == client->priv->tls)
661 client->priv->tls = tls;
662 g_object_notify (G_OBJECT (client), "tls");
666 * g_socket_client_get_tls_validation_flags:
667 * @client: a #GSocketClient.
669 * Gets the TLS validation flags used creating TLS connections via
672 * Returns: the TLS validation flags
677 g_socket_client_get_tls_validation_flags (GSocketClient *client)
679 return client->priv->tls_validation_flags;
683 * g_socket_client_set_tls_validation_flags:
684 * @client: a #GSocketClient.
685 * @flags: the validation flags
687 * Sets the TLS validation flags used when creating TLS connections
688 * via @client. The default value is %G_TLS_CERTIFICATE_VALIDATE_ALL.
693 g_socket_client_set_tls_validation_flags (GSocketClient *client,
694 GTlsCertificateFlags flags)
696 if (client->priv->tls_validation_flags != flags)
698 client->priv->tls_validation_flags = flags;
699 g_object_notify (G_OBJECT (client), "tls-validation-flags");
704 * g_socket_client_get_proxy_resolver:
705 * @client: a #GSocketClient.
707 * Gets the #GProxyResolver being used by @client. Normally, this will
708 * be the resolver returned by g_proxy_resolver_get_default(), but you
709 * can override it with g_socket_client_set_proxy_resolver().
711 * Returns: (transfer none): The #GProxyResolver being used by
717 g_socket_client_get_proxy_resolver (GSocketClient *client)
719 if (client->priv->proxy_resolver)
720 return client->priv->proxy_resolver;
722 return g_proxy_resolver_get_default ();
726 * g_socket_client_set_proxy_resolver:
727 * @client: a #GSocketClient.
728 * @proxy_resolver: (nullable): a #GProxyResolver, or %NULL for the
731 * Overrides the #GProxyResolver used by @client. You can call this if
732 * you want to use specific proxies, rather than using the system
733 * default proxy settings.
735 * Note that whether or not the proxy resolver is actually used
736 * depends on the setting of #GSocketClient:enable-proxy, which is not
737 * changed by this function (but which is %TRUE by default)
742 g_socket_client_set_proxy_resolver (GSocketClient *client,
743 GProxyResolver *proxy_resolver)
745 /* We have to be careful to avoid calling
746 * g_proxy_resolver_get_default() until we're sure we need it,
747 * because trying to load the default proxy resolver module will
748 * break some test programs that aren't expecting it (eg,
752 if (client->priv->proxy_resolver)
753 g_object_unref (client->priv->proxy_resolver);
755 client->priv->proxy_resolver = proxy_resolver;
757 if (client->priv->proxy_resolver)
758 g_object_ref (client->priv->proxy_resolver);
762 g_socket_client_class_init (GSocketClientClass *class)
764 GObjectClass *gobject_class = G_OBJECT_CLASS (class);
766 gobject_class->finalize = g_socket_client_finalize;
767 gobject_class->set_property = g_socket_client_set_property;
768 gobject_class->get_property = g_socket_client_get_property;
771 * GSocketClient::event:
772 * @client: the #GSocketClient
773 * @event: the event that is occurring
774 * @connectable: the #GSocketConnectable that @event is occurring on
775 * @connection: (nullable): the current representation of the connection
777 * Emitted when @client's activity on @connectable changes state.
778 * Among other things, this can be used to provide progress
779 * information about a network connection in the UI. The meanings of
780 * the different @event values are as follows:
782 * - %G_SOCKET_CLIENT_RESOLVING: @client is about to look up @connectable
783 * in DNS. @connection will be %NULL.
785 * - %G_SOCKET_CLIENT_RESOLVED: @client has successfully resolved
786 * @connectable in DNS. @connection will be %NULL.
788 * - %G_SOCKET_CLIENT_CONNECTING: @client is about to make a connection
789 * to a remote host; either a proxy server or the destination server
790 * itself. @connection is the #GSocketConnection, which is not yet
791 * connected. Since GLib 2.40, you can access the remote
792 * address via g_socket_connection_get_remote_address().
794 * - %G_SOCKET_CLIENT_CONNECTED: @client has successfully connected
795 * to a remote host. @connection is the connected #GSocketConnection.
797 * - %G_SOCKET_CLIENT_PROXY_NEGOTIATING: @client is about to negotiate
798 * with a proxy to get it to connect to @connectable. @connection is
799 * the #GSocketConnection to the proxy server.
801 * - %G_SOCKET_CLIENT_PROXY_NEGOTIATED: @client has negotiated a
802 * connection to @connectable through a proxy server. @connection is
803 * the stream returned from g_proxy_connect(), which may or may not
804 * be a #GSocketConnection.
806 * - %G_SOCKET_CLIENT_TLS_HANDSHAKING: @client is about to begin a TLS
807 * handshake. @connection is a #GTlsClientConnection.
809 * - %G_SOCKET_CLIENT_TLS_HANDSHAKED: @client has successfully completed
810 * the TLS handshake. @connection is a #GTlsClientConnection.
812 * - %G_SOCKET_CLIENT_COMPLETE: @client has either successfully connected
813 * to @connectable (in which case @connection is the #GSocketConnection
814 * that it will be returning to the caller) or has failed (in which
815 * case @connection is %NULL and the client is about to return an error).
817 * Each event except %G_SOCKET_CLIENT_COMPLETE may be emitted
818 * multiple times (or not at all) for a given connectable (in
819 * particular, if @client ends up attempting to connect to more than
820 * one address). However, if @client emits the #GSocketClient::event
821 * signal at all for a given connectable, that it will always emit
822 * it with %G_SOCKET_CLIENT_COMPLETE when it is done.
824 * Note that there may be additional #GSocketClientEvent values in
825 * the future; unrecognized @event values should be ignored.
830 g_signal_new (I_("event"),
831 G_TYPE_FROM_CLASS (gobject_class),
833 G_STRUCT_OFFSET (GSocketClientClass, event),
837 G_TYPE_SOCKET_CLIENT_EVENT,
838 G_TYPE_SOCKET_CONNECTABLE,
841 g_object_class_install_property (gobject_class, PROP_FAMILY,
842 g_param_spec_enum ("family",
844 P_("The sockets address family to use for socket construction"),
845 G_TYPE_SOCKET_FAMILY,
846 G_SOCKET_FAMILY_INVALID,
849 G_PARAM_STATIC_STRINGS));
851 g_object_class_install_property (gobject_class, PROP_TYPE,
852 g_param_spec_enum ("type",
854 P_("The sockets type to use for socket construction"),
856 G_SOCKET_TYPE_STREAM,
859 G_PARAM_STATIC_STRINGS));
861 g_object_class_install_property (gobject_class, PROP_PROTOCOL,
862 g_param_spec_enum ("protocol",
863 P_("Socket protocol"),
864 P_("The protocol to use for socket construction, or 0 for default"),
865 G_TYPE_SOCKET_PROTOCOL,
866 G_SOCKET_PROTOCOL_DEFAULT,
869 G_PARAM_STATIC_STRINGS));
871 g_object_class_install_property (gobject_class, PROP_LOCAL_ADDRESS,
872 g_param_spec_object ("local-address",
874 P_("The local address constructed sockets will be bound to"),
875 G_TYPE_SOCKET_ADDRESS,
878 G_PARAM_STATIC_STRINGS));
880 g_object_class_install_property (gobject_class, PROP_TIMEOUT,
881 g_param_spec_uint ("timeout",
882 P_("Socket timeout"),
883 P_("The I/O timeout for sockets, or 0 for none"),
887 G_PARAM_STATIC_STRINGS));
889 g_object_class_install_property (gobject_class, PROP_ENABLE_PROXY,
890 g_param_spec_boolean ("enable-proxy",
892 P_("Enable proxy support"),
896 G_PARAM_STATIC_STRINGS));
898 g_object_class_install_property (gobject_class, PROP_TLS,
899 g_param_spec_boolean ("tls",
901 P_("Whether to create TLS connections"),
905 G_PARAM_STATIC_STRINGS));
906 g_object_class_install_property (gobject_class, PROP_TLS_VALIDATION_FLAGS,
907 g_param_spec_flags ("tls-validation-flags",
908 P_("TLS validation flags"),
909 P_("TLS validation flags to use"),
910 G_TYPE_TLS_CERTIFICATE_FLAGS,
911 G_TLS_CERTIFICATE_VALIDATE_ALL,
914 G_PARAM_STATIC_STRINGS));
917 * GSocketClient:proxy-resolver:
919 * The proxy resolver to use
923 g_object_class_install_property (gobject_class, PROP_PROXY_RESOLVER,
924 g_param_spec_object ("proxy-resolver",
925 P_("Proxy resolver"),
926 P_("The proxy resolver to use"),
927 G_TYPE_PROXY_RESOLVER,
930 G_PARAM_STATIC_STRINGS));
934 g_socket_client_emit_event (GSocketClient *client,
935 GSocketClientEvent event,
936 GSocketConnectable *connectable,
937 GIOStream *connection)
939 g_signal_emit (client, signals[EVENT], 0,
940 event, connectable, connection);
944 * g_socket_client_connect:
945 * @client: a #GSocketClient.
946 * @connectable: a #GSocketConnectable specifying the remote address.
947 * @cancellable: (nullable): optional #GCancellable object, %NULL to ignore.
948 * @error: #GError for error reporting, or %NULL to ignore.
950 * Tries to resolve the @connectable and make a network connection to it.
952 * Upon a successful connection, a new #GSocketConnection is constructed
953 * and returned. The caller owns this new object and must drop their
954 * reference to it when finished with it.
956 * The type of the #GSocketConnection object returned depends on the type of
957 * the underlying socket that is used. For instance, for a TCP/IP connection
958 * it will be a #GTcpConnection.
960 * The socket created will be the same family as the address that the
961 * @connectable resolves to, unless family is set with g_socket_client_set_family()
962 * or indirectly via g_socket_client_set_local_address(). The socket type
963 * defaults to %G_SOCKET_TYPE_STREAM but can be set with
964 * g_socket_client_set_socket_type().
966 * If a local address is specified with g_socket_client_set_local_address() the
967 * socket will be bound to this address before connecting.
969 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
974 g_socket_client_connect (GSocketClient *client,
975 GSocketConnectable *connectable,
976 GCancellable *cancellable,
979 GIOStream *connection = NULL;
980 GSocketAddressEnumerator *enumerator = NULL;
981 GError *last_error, *tmp_error;
985 if (can_use_proxy (client))
987 enumerator = g_socket_connectable_proxy_enumerate (connectable);
988 if (client->priv->proxy_resolver &&
989 G_IS_PROXY_ADDRESS_ENUMERATOR (enumerator))
991 g_object_set (G_OBJECT (enumerator),
992 "proxy-resolver", client->priv->proxy_resolver,
997 enumerator = g_socket_connectable_enumerate (connectable);
999 while (connection == NULL)
1001 GSocketAddress *address = NULL;
1002 gboolean application_proxy = FALSE;
1004 gboolean using_proxy;
1006 if (g_cancellable_is_cancelled (cancellable))
1008 g_clear_error (error);
1009 g_cancellable_set_error_if_cancelled (cancellable, error);
1014 g_socket_client_emit_event (client, G_SOCKET_CLIENT_RESOLVING,
1016 address = g_socket_address_enumerator_next (enumerator, cancellable,
1019 if (address == NULL)
1023 g_clear_error (&last_error);
1024 g_propagate_error (error, tmp_error);
1026 else if (last_error)
1028 g_propagate_error (error, last_error);
1031 g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED,
1032 _("Unknown error on connect"));
1035 g_socket_client_emit_event (client, G_SOCKET_CLIENT_RESOLVED,
1038 using_proxy = (G_IS_PROXY_ADDRESS (address) &&
1039 client->priv->enable_proxy);
1041 /* clear error from previous attempt */
1042 g_clear_error (&last_error);
1044 socket = create_socket (client, address, &last_error);
1047 g_object_unref (address);
1051 connection = (GIOStream *)g_socket_connection_factory_create_connection (socket);
1052 g_socket_connection_set_cached_remote_address ((GSocketConnection*)connection, address);
1053 g_socket_client_emit_event (client, G_SOCKET_CLIENT_CONNECTING, connectable, connection);
1055 if (g_socket_connection_connect (G_SOCKET_CONNECTION (connection),
1056 address, cancellable, &last_error))
1058 g_socket_connection_set_cached_remote_address ((GSocketConnection*)connection, NULL);
1059 g_socket_client_emit_event (client, G_SOCKET_CLIENT_CONNECTED, connectable, connection);
1063 clarify_connect_error (last_error, connectable, address);
1064 g_object_unref (connection);
1068 if (connection && using_proxy)
1070 GProxyAddress *proxy_addr = G_PROXY_ADDRESS (address);
1071 const gchar *protocol;
1074 protocol = g_proxy_address_get_protocol (proxy_addr);
1076 /* The connection should not be anything else then TCP Connection,
1077 * but let's put a safety guard in case
1079 if (!G_IS_TCP_CONNECTION (connection))
1081 g_critical ("Trying to proxy over non-TCP connection, this is "
1082 "most likely a bug in GLib IO library.");
1084 g_set_error_literal (&last_error,
1085 G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
1086 _("Proxying over a non-TCP connection is not supported."));
1088 g_object_unref (connection);
1091 else if (g_hash_table_contains (client->priv->app_proxies, protocol))
1093 application_proxy = TRUE;
1095 else if ((proxy = g_proxy_get_default_for_protocol (protocol)))
1097 GIOStream *proxy_connection;
1099 g_socket_client_emit_event (client, G_SOCKET_CLIENT_PROXY_NEGOTIATING, connectable, connection);
1100 proxy_connection = g_proxy_connect (proxy,
1105 g_object_unref (connection);
1106 connection = proxy_connection;
1107 g_object_unref (proxy);
1110 g_socket_client_emit_event (client, G_SOCKET_CLIENT_PROXY_NEGOTIATED, connectable, connection);
1114 g_set_error (&last_error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
1115 _("Proxy protocol “%s” is not supported."),
1117 g_object_unref (connection);
1122 if (!application_proxy && connection && client->priv->tls)
1126 tlsconn = g_tls_client_connection_new (connection, connectable, &last_error);
1127 g_object_unref (connection);
1128 connection = tlsconn;
1132 g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (tlsconn),
1133 client->priv->tls_validation_flags);
1134 g_socket_client_emit_event (client, G_SOCKET_CLIENT_TLS_HANDSHAKING, connectable, connection);
1135 if (g_tls_connection_handshake (G_TLS_CONNECTION (tlsconn),
1136 cancellable, &last_error))
1138 g_socket_client_emit_event (client, G_SOCKET_CLIENT_TLS_HANDSHAKED, connectable, connection);
1142 g_object_unref (tlsconn);
1148 if (connection && !G_IS_SOCKET_CONNECTION (connection))
1150 GSocketConnection *wrapper_connection;
1152 wrapper_connection = g_tcp_wrapper_connection_new (connection, socket);
1153 g_object_unref (connection);
1154 connection = (GIOStream *)wrapper_connection;
1157 g_object_unref (socket);
1158 g_object_unref (address);
1160 g_object_unref (enumerator);
1162 g_socket_client_emit_event (client, G_SOCKET_CLIENT_COMPLETE, connectable, connection);
1163 return G_SOCKET_CONNECTION (connection);
1167 * g_socket_client_connect_to_host:
1168 * @client: a #GSocketClient
1169 * @host_and_port: the name and optionally port of the host to connect to
1170 * @default_port: the default port to connect to
1171 * @cancellable: (nullable): a #GCancellable, or %NULL
1172 * @error: a pointer to a #GError, or %NULL
1174 * This is a helper function for g_socket_client_connect().
1176 * Attempts to create a TCP connection to the named host.
1178 * @host_and_port may be in any of a number of recognized formats; an IPv6
1179 * address, an IPv4 address, or a domain name (in which case a DNS
1180 * lookup is performed). Quoting with [] is supported for all address
1181 * types. A port override may be specified in the usual way with a
1182 * colon. Ports may be given as decimal numbers or symbolic names (in
1183 * which case an /etc/services lookup is performed).
1185 * If no port override is given in @host_and_port then @default_port will be
1186 * used as the port number to connect to.
1188 * In general, @host_and_port is expected to be provided by the user (allowing
1189 * them to give the hostname, and a port override if necessary) and
1190 * @default_port is expected to be provided by the application.
1192 * In the case that an IP address is given, a single connection
1193 * attempt is made. In the case that a name is given, multiple
1194 * connection attempts may be made, in turn and according to the
1195 * number of address records in DNS, until a connection succeeds.
1197 * Upon a successful connection, a new #GSocketConnection is constructed
1198 * and returned. The caller owns this new object and must drop their
1199 * reference to it when finished with it.
1201 * In the event of any failure (DNS error, service not found, no hosts
1202 * connectable) %NULL is returned and @error (if non-%NULL) is set
1205 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
1210 g_socket_client_connect_to_host (GSocketClient *client,
1211 const gchar *host_and_port,
1212 guint16 default_port,
1213 GCancellable *cancellable,
1216 GSocketConnectable *connectable;
1217 GSocketConnection *connection;
1219 connectable = g_network_address_parse (host_and_port, default_port, error);
1220 if (connectable == NULL)
1223 connection = g_socket_client_connect (client, connectable,
1224 cancellable, error);
1225 g_object_unref (connectable);
1231 * g_socket_client_connect_to_service:
1232 * @client: a #GSocketConnection
1233 * @domain: a domain name
1234 * @service: the name of the service to connect to
1235 * @cancellable: (nullable): a #GCancellable, or %NULL
1236 * @error: a pointer to a #GError, or %NULL
1238 * Attempts to create a TCP connection to a service.
1240 * This call looks up the SRV record for @service at @domain for the
1241 * "tcp" protocol. It then attempts to connect, in turn, to each of
1242 * the hosts providing the service until either a connection succeeds
1243 * or there are no hosts remaining.
1245 * Upon a successful connection, a new #GSocketConnection is constructed
1246 * and returned. The caller owns this new object and must drop their
1247 * reference to it when finished with it.
1249 * In the event of any failure (DNS error, service not found, no hosts
1250 * connectable) %NULL is returned and @error (if non-%NULL) is set
1253 * Returns: (transfer full): a #GSocketConnection if successful, or %NULL on error
1256 g_socket_client_connect_to_service (GSocketClient *client,
1257 const gchar *domain,
1258 const gchar *service,
1259 GCancellable *cancellable,
1262 GSocketConnectable *connectable;
1263 GSocketConnection *connection;
1265 connectable = g_network_service_new (service, "tcp", domain);
1266 connection = g_socket_client_connect (client, connectable,
1267 cancellable, error);
1268 g_object_unref (connectable);
1274 * g_socket_client_connect_to_uri:
1275 * @client: a #GSocketClient
1276 * @uri: A network URI
1277 * @default_port: the default port to connect to
1278 * @cancellable: (nullable): a #GCancellable, or %NULL
1279 * @error: a pointer to a #GError, or %NULL
1281 * This is a helper function for g_socket_client_connect().
1283 * Attempts to create a TCP connection with a network URI.
1285 * @uri may be any valid URI containing an "authority" (hostname/port)
1286 * component. If a port is not specified in the URI, @default_port
1287 * will be used. TLS will be negotiated if #GSocketClient:tls is %TRUE.
1288 * (#GSocketClient does not know to automatically assume TLS for
1289 * certain URI schemes.)
1291 * Using this rather than g_socket_client_connect() or
1292 * g_socket_client_connect_to_host() allows #GSocketClient to
1293 * determine when to use application-specific proxy protocols.
1295 * Upon a successful connection, a new #GSocketConnection is constructed
1296 * and returned. The caller owns this new object and must drop their
1297 * reference to it when finished with it.
1299 * In the event of any failure (DNS error, service not found, no hosts
1300 * connectable) %NULL is returned and @error (if non-%NULL) is set
1303 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
1308 g_socket_client_connect_to_uri (GSocketClient *client,
1310 guint16 default_port,
1311 GCancellable *cancellable,
1314 GSocketConnectable *connectable;
1315 GSocketConnection *connection;
1317 connectable = g_network_address_parse_uri (uri, default_port, error);
1318 if (connectable == NULL)
1321 connection = g_socket_client_connect (client, connectable,
1322 cancellable, error);
1323 g_object_unref (connectable);
1330 GTask *task; /* unowned */
1331 GSocketClient *client;
1333 GSocketConnectable *connectable;
1334 GSocketAddressEnumerator *enumerator;
1335 GProxyAddress *proxy_addr;
1337 GIOStream *connection;
1339 GSList *connection_attempts;
1343 } GSocketClientAsyncConnectData;
1345 static void connection_attempt_unref (gpointer attempt);
1348 g_socket_client_async_connect_data_free (GSocketClientAsyncConnectData *data)
1351 g_clear_object (&data->connectable);
1352 g_clear_object (&data->enumerator);
1353 g_clear_object (&data->proxy_addr);
1354 g_clear_object (&data->socket);
1355 g_clear_object (&data->connection);
1356 g_slist_free_full (data->connection_attempts, connection_attempt_unref);
1358 g_clear_error (&data->last_error);
1360 g_slice_free (GSocketClientAsyncConnectData, data);
1365 GSocketAddress *address;
1367 GIOStream *connection;
1368 GSocketClientAsyncConnectData *data; /* unowned */
1369 GSource *timeout_source;
1370 GCancellable *cancellable;
1372 } ConnectionAttempt;
1374 static ConnectionAttempt *
1375 connection_attempt_new (void)
1377 ConnectionAttempt *attempt = g_new0 (ConnectionAttempt, 1);
1378 g_ref_count_init (&attempt->ref);
1382 static ConnectionAttempt *
1383 connection_attempt_ref (ConnectionAttempt *attempt)
1385 g_ref_count_inc (&attempt->ref);
1390 connection_attempt_unref (gpointer pointer)
1392 ConnectionAttempt *attempt = pointer;
1393 if (g_ref_count_dec (&attempt->ref))
1395 g_clear_object (&attempt->address);
1396 g_clear_object (&attempt->socket);
1397 g_clear_object (&attempt->connection);
1398 g_clear_object (&attempt->cancellable);
1399 if (attempt->timeout_source)
1401 g_source_destroy (attempt->timeout_source);
1402 g_source_unref (attempt->timeout_source);
1409 connection_attempt_remove (ConnectionAttempt *attempt)
1411 attempt->data->connection_attempts = g_slist_remove (attempt->data->connection_attempts, attempt);
1412 connection_attempt_unref (attempt);
1416 g_socket_client_async_connect_complete (GSocketClientAsyncConnectData *data)
1418 g_assert (data->connection);
1420 if (!G_IS_SOCKET_CONNECTION (data->connection))
1422 GSocketConnection *wrapper_connection;
1424 wrapper_connection = g_tcp_wrapper_connection_new (data->connection, data->socket);
1425 g_object_unref (data->connection);
1426 data->connection = (GIOStream *)wrapper_connection;
1429 if (!g_task_return_error_if_cancelled (data->task))
1431 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_COMPLETE, data->connectable, data->connection);
1432 g_task_return_pointer (data->task, g_steal_pointer (&data->connection), g_object_unref);
1435 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_COMPLETE, data->connectable, NULL);
1437 data->completed = TRUE;
1438 g_object_unref (data->task);
1443 g_socket_client_enumerator_callback (GObject *object,
1444 GAsyncResult *result,
1445 gpointer user_data);
1448 set_last_error (GSocketClientAsyncConnectData *data,
1451 g_clear_error (&data->last_error);
1452 data->last_error = error;
1456 enumerator_next_async (GSocketClientAsyncConnectData *data,
1457 gboolean add_task_ref)
1459 /* We need to cleanup the state */
1460 g_clear_object (&data->socket);
1461 g_clear_object (&data->proxy_addr);
1462 g_clear_object (&data->connection);
1464 /* Each enumeration takes a ref. This arg just avoids repeated unrefs when
1465 an enumeration starts another enumeration */
1467 g_object_ref (data->task);
1469 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_RESOLVING, data->connectable, NULL);
1470 g_socket_address_enumerator_next_async (data->enumerator,
1471 g_task_get_cancellable (data->task),
1472 g_socket_client_enumerator_callback,
1477 g_socket_client_tls_handshake_callback (GObject *object,
1478 GAsyncResult *result,
1481 GSocketClientAsyncConnectData *data = user_data;
1483 if (g_tls_connection_handshake_finish (G_TLS_CONNECTION (object),
1487 g_object_unref (data->connection);
1488 data->connection = G_IO_STREAM (object);
1490 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_TLS_HANDSHAKED, data->connectable, data->connection);
1491 g_socket_client_async_connect_complete (data);
1495 g_object_unref (object);
1496 enumerator_next_async (data, FALSE);
1501 g_socket_client_tls_handshake (GSocketClientAsyncConnectData *data)
1505 if (!data->client->priv->tls)
1507 g_socket_client_async_connect_complete (data);
1511 tlsconn = g_tls_client_connection_new (data->connection,
1516 g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (tlsconn),
1517 data->client->priv->tls_validation_flags);
1518 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_TLS_HANDSHAKING, data->connectable, G_IO_STREAM (tlsconn));
1519 g_tls_connection_handshake_async (G_TLS_CONNECTION (tlsconn),
1521 g_task_get_cancellable (data->task),
1522 g_socket_client_tls_handshake_callback,
1527 enumerator_next_async (data, FALSE);
1532 g_socket_client_proxy_connect_callback (GObject *object,
1533 GAsyncResult *result,
1536 GSocketClientAsyncConnectData *data = user_data;
1538 g_object_unref (data->connection);
1539 data->connection = g_proxy_connect_finish (G_PROXY (object),
1542 if (data->connection)
1544 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_PROXY_NEGOTIATED, data->connectable, data->connection);
1548 enumerator_next_async (data, FALSE);
1552 g_socket_client_tls_handshake (data);
1556 task_completed_or_cancelled (GSocketClientAsyncConnectData *data)
1558 GTask *task = data->task;
1559 GCancellable *cancellable = g_task_get_cancellable (task);
1560 GError *error = NULL;
1562 if (data->completed)
1564 else if (g_cancellable_set_error_if_cancelled (cancellable, &error))
1566 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_COMPLETE, data->connectable, NULL);
1567 g_task_return_error (task, g_steal_pointer (&error));
1568 data->completed = TRUE;
1576 g_socket_client_connected_callback (GObject *source,
1577 GAsyncResult *result,
1580 ConnectionAttempt *attempt = user_data;
1581 GSocketClientAsyncConnectData *data = attempt->data;
1583 GError *error = NULL;
1585 const gchar *protocol;
1587 if (task_completed_or_cancelled (data) || g_cancellable_is_cancelled (attempt->cancellable))
1589 g_object_unref (data->task);
1590 connection_attempt_unref (attempt);
1594 if (attempt->timeout_source)
1596 g_source_destroy (attempt->timeout_source);
1597 g_clear_pointer (&attempt->timeout_source, g_source_unref);
1600 if (!g_socket_connection_connect_finish (G_SOCKET_CONNECTION (source),
1603 if (!g_cancellable_is_cancelled (attempt->cancellable))
1605 clarify_connect_error (error, data->connectable, attempt->address);
1606 set_last_error (data, error);
1607 connection_attempt_remove (attempt);
1608 enumerator_next_async (data, FALSE);
1612 g_clear_error (&error);
1613 g_object_unref (data->task);
1614 connection_attempt_unref (attempt);
1620 data->socket = g_steal_pointer (&attempt->socket);
1621 data->connection = g_steal_pointer (&attempt->connection);
1623 for (l = data->connection_attempts; l; l = g_slist_next (l))
1625 ConnectionAttempt *attempt_entry = l->data;
1626 g_cancellable_cancel (attempt_entry->cancellable);
1627 connection_attempt_unref (attempt_entry);
1629 g_slist_free (data->connection_attempts);
1630 data->connection_attempts = NULL;
1631 connection_attempt_unref (attempt);
1633 g_socket_connection_set_cached_remote_address ((GSocketConnection*)data->connection, NULL);
1634 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_CONNECTED, data->connectable, data->connection);
1636 /* wrong, but backward compatible */
1637 g_socket_set_blocking (data->socket, TRUE);
1639 if (!data->proxy_addr)
1641 g_socket_client_tls_handshake (data);
1645 protocol = g_proxy_address_get_protocol (data->proxy_addr);
1647 /* The connection should not be anything other than TCP,
1648 * but let's put a safety guard in case
1650 if (!G_IS_TCP_CONNECTION (data->connection))
1652 g_critical ("Trying to proxy over non-TCP connection, this is "
1653 "most likely a bug in GLib IO library.");
1655 g_set_error_literal (&data->last_error,
1656 G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
1657 _("Proxying over a non-TCP connection is not supported."));
1659 enumerator_next_async (data, FALSE);
1661 else if (g_hash_table_contains (data->client->priv->app_proxies, protocol))
1663 /* Simply complete the connection, we don't want to do TLS handshake
1664 * as the application proxy handling may need proxy handshake first */
1665 g_socket_client_async_connect_complete (data);
1667 else if ((proxy = g_proxy_get_default_for_protocol (protocol)))
1669 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_PROXY_NEGOTIATING, data->connectable, data->connection);
1670 g_proxy_connect_async (proxy,
1673 g_task_get_cancellable (data->task),
1674 g_socket_client_proxy_connect_callback,
1676 g_object_unref (proxy);
1680 g_clear_error (&data->last_error);
1682 g_set_error (&data->last_error, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED,
1683 _("Proxy protocol “%s” is not supported."),
1686 enumerator_next_async (data, FALSE);
1691 on_connection_attempt_timeout (gpointer data)
1693 ConnectionAttempt *attempt = data;
1695 enumerator_next_async (attempt->data, TRUE);
1697 g_clear_pointer (&attempt->timeout_source, g_source_unref);
1698 return G_SOURCE_REMOVE;
1702 on_connection_cancelled (GCancellable *cancellable,
1705 GCancellable *attempt_cancellable = data;
1707 g_cancellable_cancel (attempt_cancellable);
1711 g_socket_client_enumerator_callback (GObject *object,
1712 GAsyncResult *result,
1715 GSocketClientAsyncConnectData *data = user_data;
1716 GSocketAddress *address = NULL;
1718 ConnectionAttempt *attempt;
1719 GError *error = NULL;
1721 if (task_completed_or_cancelled (data))
1723 g_object_unref (data->task);
1727 address = g_socket_address_enumerator_next_finish (data->enumerator,
1729 if (address == NULL)
1731 if (data->connection_attempts)
1733 g_object_unref (data->task);
1737 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_COMPLETE, data->connectable, NULL);
1738 data->completed = TRUE;
1741 if (data->last_error)
1743 error = data->last_error;
1744 data->last_error = NULL;
1748 g_set_error_literal (&error, G_IO_ERROR, G_IO_ERROR_FAILED,
1749 _("Unknown error on connect"));
1752 g_task_return_error (data->task, error);
1753 g_object_unref (data->task);
1757 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_RESOLVED,
1758 data->connectable, NULL);
1760 if (G_IS_PROXY_ADDRESS (address) &&
1761 data->client->priv->enable_proxy)
1762 data->proxy_addr = g_object_ref (G_PROXY_ADDRESS (address));
1764 g_clear_error (&data->last_error);
1766 socket = create_socket (data->client, address, &data->last_error);
1769 g_object_unref (address);
1770 enumerator_next_async (data, FALSE);
1774 attempt = connection_attempt_new ();
1775 attempt->data = data;
1776 attempt->socket = socket;
1777 attempt->address = address;
1778 attempt->cancellable = g_cancellable_new ();
1779 attempt->connection = (GIOStream *)g_socket_connection_factory_create_connection (socket);
1780 attempt->timeout_source = g_timeout_source_new (HAPPY_EYEBALLS_CONNECTION_ATTEMPT_TIMEOUT_MS);
1781 g_source_set_callback (attempt->timeout_source, on_connection_attempt_timeout, attempt, NULL);
1782 g_source_attach (attempt->timeout_source, g_main_context_get_thread_default ());
1783 data->connection_attempts = g_slist_append (data->connection_attempts, attempt);
1785 if (g_task_get_cancellable (data->task))
1786 g_cancellable_connect (g_task_get_cancellable (data->task), G_CALLBACK (on_connection_cancelled),
1787 g_object_ref (attempt->cancellable), g_object_unref);
1789 g_socket_connection_set_cached_remote_address ((GSocketConnection *)attempt->connection, address);
1790 g_socket_client_emit_event (data->client, G_SOCKET_CLIENT_CONNECTING, data->connectable, attempt->connection);
1791 g_socket_connection_connect_async (G_SOCKET_CONNECTION (attempt->connection),
1793 attempt->cancellable,
1794 g_socket_client_connected_callback, connection_attempt_ref (attempt));
1798 * g_socket_client_connect_async:
1799 * @client: a #GSocketClient
1800 * @connectable: a #GSocketConnectable specifying the remote address.
1801 * @cancellable: (nullable): a #GCancellable, or %NULL
1802 * @callback: (scope async): a #GAsyncReadyCallback
1803 * @user_data: (closure): user data for the callback
1805 * This is the asynchronous version of g_socket_client_connect().
1807 * When the operation is finished @callback will be
1808 * called. You can then call g_socket_client_connect_finish() to get
1809 * the result of the operation.
1814 g_socket_client_connect_async (GSocketClient *client,
1815 GSocketConnectable *connectable,
1816 GCancellable *cancellable,
1817 GAsyncReadyCallback callback,
1820 GSocketClientAsyncConnectData *data;
1822 g_return_if_fail (G_IS_SOCKET_CLIENT (client));
1824 data = g_slice_new0 (GSocketClientAsyncConnectData);
1825 data->client = client;
1826 data->connectable = g_object_ref (connectable);
1828 if (can_use_proxy (client))
1830 data->enumerator = g_socket_connectable_proxy_enumerate (connectable);
1831 if (client->priv->proxy_resolver &&
1832 G_IS_PROXY_ADDRESS_ENUMERATOR (data->enumerator))
1834 g_object_set (G_OBJECT (data->enumerator),
1835 "proxy-resolver", client->priv->proxy_resolver,
1840 data->enumerator = g_socket_connectable_enumerate (connectable);
1842 /* The flow and ownership here isn't quite obvious:
1843 - The task starts an async attempt to connect.
1844 - Each attempt holds a single ref on task.
1845 - Each attempt may create new attempts by timing out (not a failure) so
1846 there are multiple attempts happening in parallel.
1847 - Upon failure an attempt will start a new attempt that steals its ref
1848 until there are no more attempts left and it drops its ref.
1849 - Upon success it will cancel all other attempts and continue on
1850 to the rest of the connection (tls, proxies, etc) which do not
1851 happen in parallel and at the very end drop its ref.
1852 - Upon cancellation an attempt drops its ref.
1855 data->task = g_task_new (client, cancellable, callback, user_data);
1856 g_task_set_check_cancellable (data->task, FALSE); /* We handle this manually */
1857 g_task_set_source_tag (data->task, g_socket_client_connect_async);
1858 g_task_set_task_data (data->task, data, (GDestroyNotify)g_socket_client_async_connect_data_free);
1860 enumerator_next_async (data, FALSE);
1864 * g_socket_client_connect_to_host_async:
1865 * @client: a #GSocketClient
1866 * @host_and_port: the name and optionally the port of the host to connect to
1867 * @default_port: the default port to connect to
1868 * @cancellable: (nullable): a #GCancellable, or %NULL
1869 * @callback: (scope async): a #GAsyncReadyCallback
1870 * @user_data: (closure): user data for the callback
1872 * This is the asynchronous version of g_socket_client_connect_to_host().
1874 * When the operation is finished @callback will be
1875 * called. You can then call g_socket_client_connect_to_host_finish() to get
1876 * the result of the operation.
1881 g_socket_client_connect_to_host_async (GSocketClient *client,
1882 const gchar *host_and_port,
1883 guint16 default_port,
1884 GCancellable *cancellable,
1885 GAsyncReadyCallback callback,
1888 GSocketConnectable *connectable;
1892 connectable = g_network_address_parse (host_and_port, default_port,
1894 if (connectable == NULL)
1896 g_task_report_error (client, callback, user_data,
1897 g_socket_client_connect_to_host_async,
1902 g_socket_client_connect_async (client,
1903 connectable, cancellable,
1904 callback, user_data);
1905 g_object_unref (connectable);
1910 * g_socket_client_connect_to_service_async:
1911 * @client: a #GSocketClient
1912 * @domain: a domain name
1913 * @service: the name of the service to connect to
1914 * @cancellable: (nullable): a #GCancellable, or %NULL
1915 * @callback: (scope async): a #GAsyncReadyCallback
1916 * @user_data: (closure): user data for the callback
1918 * This is the asynchronous version of
1919 * g_socket_client_connect_to_service().
1924 g_socket_client_connect_to_service_async (GSocketClient *client,
1925 const gchar *domain,
1926 const gchar *service,
1927 GCancellable *cancellable,
1928 GAsyncReadyCallback callback,
1931 GSocketConnectable *connectable;
1933 connectable = g_network_service_new (service, "tcp", domain);
1934 g_socket_client_connect_async (client,
1935 connectable, cancellable,
1936 callback, user_data);
1937 g_object_unref (connectable);
1941 * g_socket_client_connect_to_uri_async:
1942 * @client: a #GSocketClient
1943 * @uri: a network uri
1944 * @default_port: the default port to connect to
1945 * @cancellable: (nullable): a #GCancellable, or %NULL
1946 * @callback: (scope async): a #GAsyncReadyCallback
1947 * @user_data: (closure): user data for the callback
1949 * This is the asynchronous version of g_socket_client_connect_to_uri().
1951 * When the operation is finished @callback will be
1952 * called. You can then call g_socket_client_connect_to_uri_finish() to get
1953 * the result of the operation.
1958 g_socket_client_connect_to_uri_async (GSocketClient *client,
1960 guint16 default_port,
1961 GCancellable *cancellable,
1962 GAsyncReadyCallback callback,
1965 GSocketConnectable *connectable;
1969 connectable = g_network_address_parse_uri (uri, default_port, &error);
1970 if (connectable == NULL)
1972 g_task_report_error (client, callback, user_data,
1973 g_socket_client_connect_to_uri_async,
1978 g_socket_client_connect_async (client,
1979 connectable, cancellable,
1980 callback, user_data);
1981 g_object_unref (connectable);
1987 * g_socket_client_connect_finish:
1988 * @client: a #GSocketClient.
1989 * @result: a #GAsyncResult.
1990 * @error: a #GError location to store the error occurring, or %NULL to
1993 * Finishes an async connect operation. See g_socket_client_connect_async()
1995 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
2000 g_socket_client_connect_finish (GSocketClient *client,
2001 GAsyncResult *result,
2004 g_return_val_if_fail (g_task_is_valid (result, client), NULL);
2006 return g_task_propagate_pointer (G_TASK (result), error);
2010 * g_socket_client_connect_to_host_finish:
2011 * @client: a #GSocketClient.
2012 * @result: a #GAsyncResult.
2013 * @error: a #GError location to store the error occurring, or %NULL to
2016 * Finishes an async connect operation. See g_socket_client_connect_to_host_async()
2018 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
2023 g_socket_client_connect_to_host_finish (GSocketClient *client,
2024 GAsyncResult *result,
2027 return g_socket_client_connect_finish (client, result, error);
2031 * g_socket_client_connect_to_service_finish:
2032 * @client: a #GSocketClient.
2033 * @result: a #GAsyncResult.
2034 * @error: a #GError location to store the error occurring, or %NULL to
2037 * Finishes an async connect operation. See g_socket_client_connect_to_service_async()
2039 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
2044 g_socket_client_connect_to_service_finish (GSocketClient *client,
2045 GAsyncResult *result,
2048 return g_socket_client_connect_finish (client, result, error);
2052 * g_socket_client_connect_to_uri_finish:
2053 * @client: a #GSocketClient.
2054 * @result: a #GAsyncResult.
2055 * @error: a #GError location to store the error occurring, or %NULL to
2058 * Finishes an async connect operation. See g_socket_client_connect_to_uri_async()
2060 * Returns: (transfer full): a #GSocketConnection on success, %NULL on error.
2065 g_socket_client_connect_to_uri_finish (GSocketClient *client,
2066 GAsyncResult *result,
2069 return g_socket_client_connect_finish (client, result, error);
2073 * g_socket_client_add_application_proxy:
2074 * @client: a #GSocketClient
2075 * @protocol: The proxy protocol
2077 * Enable proxy protocols to be handled by the application. When the
2078 * indicated proxy protocol is returned by the #GProxyResolver,
2079 * #GSocketClient will consider this protocol as supported but will
2080 * not try to find a #GProxy instance to handle handshaking. The
2081 * application must check for this case by calling
2082 * g_socket_connection_get_remote_address() on the returned
2083 * #GSocketConnection, and seeing if it's a #GProxyAddress of the
2084 * appropriate type, to determine whether or not it needs to handle
2085 * the proxy handshaking itself.
2087 * This should be used for proxy protocols that are dialects of
2088 * another protocol such as HTTP proxy. It also allows cohabitation of
2089 * proxy protocols that are reused between protocols. A good example
2090 * is HTTP. It can be used to proxy HTTP, FTP and Gopher and can also
2091 * be use as generic socket proxy through the HTTP CONNECT method.
2093 * When the proxy is detected as being an application proxy, TLS handshake
2094 * will be skipped. This is required to let the application do the proxy
2095 * specific handshake.
2098 g_socket_client_add_application_proxy (GSocketClient *client,
2099 const gchar *protocol)
2101 g_hash_table_add (client->priv->app_proxies, g_strdup (protocol));