# HG changeset patch
# Node ID 8501f1c77a0c
# Parent  b47d957f53bf
diff --git a/ibis-cli/ibiscli.c b/ibis-cli/ibiscli.c
--- a/ibis-cli/ibiscli.c
+++ b/ibis-cli/ibiscli.c
@@ -125,7 +125,8 @@
 		g_clear_object(&hasl_context);
 	}
 
-	ibis_client_connect(client, server, (guint16)port, password, tls, NULL);
+	ibis_client_connect(client, server, (guint16)port, password, tls, NULL,
+	                    NULL);
 }
 
 static void
diff --git a/ibis/ibisclient.h b/ibis/ibisclient.h
--- a/ibis/ibisclient.h
+++ b/ibis/ibisclient.h
@@ -72,6 +72,7 @@
  * @port: The port to connect to.
  * @password: (nullable): The optional server password to use.
  * @tls: Whether or not to use a TLS connection.
+ * @cancellable: (transfer none) (nullable): A [class@Gio.Cancellable].
  * @proxy_resolver: (transfer none) (nullable): A [iface@Gio.ProxyResolver].
  *
  * Attempts to connect to @hostname on @port.
@@ -81,7 +82,7 @@
  * Since: 0.1
  */
 IBIS_AVAILABLE_IN_0_1
-void ibis_client_connect(IbisClient *client, const char *hostname, guint16 port, const char *password, gboolean tls, GProxyResolver *proxy_resolver);
+void ibis_client_connect(IbisClient *client, const char *hostname, guint16 port, const char *password, gboolean tls, GCancellable *cancellable, GProxyResolver *proxy_resolver);
 
 /**
  * ibis_client_disconnect:
@@ -304,6 +305,7 @@
  * @client: The instance.
  * @stream: The [class@Gio.IOStream] to process.
  * @password: (nullable): The optional server password to use.
+ * @cancellable: (transfer none) (nullable): A [class@Gio.Cancellable] to use.
  *
  * Starts @client.
  *
@@ -315,7 +317,7 @@
  * Since: 0.1
  */
 IBIS_AVAILABLE_IN_0_1
-void ibis_client_start(IbisClient *client, GIOStream *stream, const char *password);
+void ibis_client_start(IbisClient *client, GIOStream *stream, const char *password, GCancellable *cancellable);
 
 /**
  * ibis_client_write:
diff --git a/ibis/ibisclient.c b/ibis/ibisclient.c
--- a/ibis/ibisclient.c
+++ b/ibis/ibisclient.c
@@ -248,7 +248,8 @@
 
 		password = g_object_get_data(G_OBJECT(client), "ibis-password");
 
-		ibis_client_start(client, G_IO_STREAM(connection), password);
+		ibis_client_start(client, G_IO_STREAM(connection), password,
+		                  client->cancellable);
 	}
 
 	g_object_set_data(G_OBJECT(client), "ibis-password", NULL);
@@ -550,6 +551,7 @@
 void
 ibis_client_connect(IbisClient *client, const char *hostname, guint16 port,
                     const char *password, gboolean tls,
+                    GCancellable *cancellable,
                     GProxyResolver *proxy_resolver)
 {
 	GSocketClient *socket_client = NULL;
@@ -561,13 +563,13 @@
 	g_socket_client_set_proxy_resolver(socket_client, proxy_resolver);
 	g_socket_client_set_tls(socket_client, tls);
 
-	client->cancellable = g_cancellable_new();
-
 	if(!ibis_str_is_empty(password)) {
 		g_object_set_data_full(G_OBJECT(client), "ibis-password",
 		                       g_strdup(password), g_free);
 	}
 
+	g_set_object(&client->cancellable, cancellable);
+
 	g_socket_client_connect_to_host_async(socket_client, hostname, port,
 	                                      client->cancellable,
 	                                      ibis_client_connect_cb, client);
@@ -579,12 +581,11 @@
 	GError *close_error = NULL;
 
 	g_return_if_fail(IBIS_IS_CLIENT(client));
-	g_return_if_fail(client->connected == TRUE);
 
 	/* Disable the capabilities handler. */
 	ibis_capabilities_stop(client->capabilities);
 
-	if(error == NULL) {
+	if(error == NULL && client->connected) {
 		IbisMessage *msg = NULL;
 
 		msg = ibis_message_new(IBIS_MSG_QUIT);
@@ -632,6 +633,7 @@
 
 	ibis_client_set_connected(client, FALSE);
 
+	g_cancellable_cancel(client->cancellable);
 	g_clear_object(&client->cancellable);
 
 	g_object_thaw_notify(G_OBJECT(client));
@@ -764,7 +766,8 @@
 }
 
 void
-ibis_client_start(IbisClient *client, GIOStream *stream, const char *password)
+ibis_client_start(IbisClient *client, GIOStream *stream, const char *password,
+                  GCancellable *cancellable)
 {
 	GInputStream *input = NULL;
 	GOutputStream *output = NULL;
@@ -773,6 +776,11 @@
 	g_return_if_fail(G_IS_IO_STREAM(stream));
 	g_return_if_fail(client->connected == FALSE);
 
+	g_set_object(&client->cancellable, cancellable);
+	if(!G_IS_CANCELLABLE(client->cancellable)) {
+		client->cancellable = g_cancellable_new();
+	}
+
 	/* Clear any previous error. */
 	ibis_client_set_error(client, NULL);
 
