diff options
author | Michael Catanzaro <mcatanzaro@igalia.com> | 2018-07-24 12:57:46 -0500 |
---|---|---|
committer | Michael Catanzaro <mcatanzaro@igalia.com> | 2018-07-24 12:57:46 -0500 |
commit | 2c68f7d379098d4a67c9db88f3fd00fca6d9e222 (patch) | |
tree | 3264f2585dcec7681c6f5563a6f4056496784d25 | |
parent | 3ba8fc30939bc246e3ec605bffd49b1bf5a731f5 (diff) | |
download | glib-networking-wip/verification.tar.gz |
Good progresswip/verification
-rw-r--r-- | tls/gnutls/gtlsconnection-gnutls.c | 112 | ||||
-rw-r--r-- | tls/gnutls/gtlsinputstream-gnutls.c | 1 |
2 files changed, 48 insertions, 65 deletions
diff --git a/tls/gnutls/gtlsconnection-gnutls.c b/tls/gnutls/gtlsconnection-gnutls.c index bb0ebfc..d618abc 100644 --- a/tls/gnutls/gtlsconnection-gnutls.c +++ b/tls/gnutls/gtlsconnection-gnutls.c @@ -749,7 +749,6 @@ claim_op (GTlsConnectionGnutls *gnutls, if (g_cancellable_set_error_if_cancelled (cancellable, error)) return FALSE; -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); switch (op) { @@ -783,7 +782,6 @@ GTLS_DEBUG(gnutls, "%s: op=CLOSE_BOTH", __FUNCTION__); GTLS_DEBUG(gnutls, "Connection is closed"); g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_CLOSED, _("Connection is closed")); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return FALSE; } @@ -796,7 +794,6 @@ GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); GTLS_DEBUG(gnutls, "Handshake error: %s", priv->handshake_error->message); if (error) *error = g_error_copy (priv->handshake_error); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return FALSE; } @@ -814,7 +811,6 @@ GTLS_DEBUG(gnutls, "Diverted into implicit handshake..."); if (!do_implicit_handshake (gnutls, timeout, cancellable, error)) { GTLS_DEBUG(gnutls, "Implicit handshake failed! Oh noo! error=%s", (*error)->message); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return FALSE; } @@ -827,14 +823,13 @@ GTLS_DEBUG(gnutls, "Implicit handshake successful"); GError *my_error = NULL; gboolean success; +GTLS_DEBUG(gnutls, "%s: need_finish_handshake=FALSE", __FUNCTION__); priv->need_finish_handshake = FALSE; -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); success = finish_handshake (gnutls, priv->implicit_handshake, &my_error); g_clear_object (&priv->implicit_handshake); g_clear_pointer (&priv->handshake_context, g_main_context_unref); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); if (op != G_TLS_CONNECTION_GNUTLS_OP_CLOSE_BOTH && @@ -844,7 +839,6 @@ GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); { g_propagate_error (error, my_error); GTLS_DEBUG(gnutls, "Oh no, finish implicit handshake failed: %s", (*error)->message); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return FALSE; } @@ -869,7 +863,6 @@ GTLS_DEBUG(gnutls, "Read/write/handshake when already read/write/handshaking in g_cancellable_reset (priv->waiting_for_op); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); if (timeout == 0) @@ -954,7 +947,6 @@ GTLS_DEBUG(gnutls, "Claimed non-read op, writing=true!"); priv->writing = TRUE; } -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return TRUE; } @@ -965,7 +957,6 @@ yield_op (GTlsConnectionGnutls *gnutls, { GTlsConnectionGnutlsPrivate *priv = g_tls_connection_gnutls_get_instance_private (gnutls); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); if (op == G_TLS_CONNECTION_GNUTLS_OP_HANDSHAKE) @@ -998,7 +989,6 @@ GTLS_DEBUG(gnutls, "Yielded non-read op, writing=false!"); } g_cancellable_cancel (priv->waiting_for_op); -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); } @@ -1116,11 +1106,9 @@ GTLS_DEBUG(gnutls, "%s: my_error code=%d (%s)", __FUNCTION__, my_error->code, my return GNUTLS_E_PULL_ERROR; } -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); if (!priv->handshaking) priv->need_handshake = TRUE; -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); return status; } @@ -1292,7 +1280,6 @@ GTLS_DEBUG(gnutls_source->gnutls, "source=%p already destroyed!", gnutls_source) return; } -GTLS_DEBUG(gnutls_source->gnutls, "%s: source=%p locking op_mutex", __FUNCTION__, gnutls_source); g_mutex_lock (&priv->op_mutex); if (((gnutls_source->condition & G_IO_IN) && priv->reading) || ((gnutls_source->condition & G_IO_OUT) && priv->writing) || @@ -1306,7 +1293,6 @@ GTLS_DEBUG(gnutls_source->gnutls, "%s: source=%p locking op_mutex", __FUNCTION__ io_waiting = TRUE; else io_waiting = FALSE; -GTLS_DEBUG(gnutls_source->gnutls, "%s: source=%p unlocking op_mutex", __FUNCTION__, gnutls_source); g_mutex_unlock (&priv->op_mutex); if (op_waiting == gnutls_source->op_waiting && @@ -1372,7 +1358,7 @@ gnutls_source_finalize (GSource *source) { GTlsConnectionGnutlsSource *gnutls_source = (GTlsConnectionGnutlsSource *)source; -GTLS_DEBUG(gnutls_source->gnutls, "%s", __FUNCTION__); +GTLS_DEBUG(gnutls_source->gnutls, "%s source=%p", __FUNCTION__, source); g_object_unref (gnutls_source->gnutls); g_source_unref (gnutls_source->child_source); @@ -1459,8 +1445,6 @@ g_tls_connection_gnutls_create_source (GTlsConnectionGnutls *gnutls, GSource *source, *cancellable_source; GTlsConnectionGnutlsSource *gnutls_source; -GTLS_DEBUG(gnutls, "%s", __FUNCTION__); - if (g_tls_connection_gnutls_is_dtls (gnutls)) { source = g_source_new (&gnutls_dtls_source_funcs, @@ -1471,6 +1455,7 @@ GTLS_DEBUG(gnutls, "%s", __FUNCTION__); source = g_source_new (&gnutls_tls_source_funcs, sizeof (GTlsConnectionGnutlsSource)); } +GTLS_DEBUG(gnutls, "%s new gnutls_source=%p", __FUNCTION__, source); g_source_set_name (source, "GTlsConnectionGnutlsSource"); gnutls_source = (GTlsConnectionGnutlsSource *)source; gnutls_source->gnutls = g_object_ref (gnutls); @@ -1964,7 +1949,6 @@ verify_certificate_cb (gnutls_session_t session) GTlsConnectionGnutls *gnutls = gnutls_session_get_ptr (session); GTlsConnectionGnutlsPrivate *priv = g_tls_connection_gnutls_get_instance_private (gnutls); gboolean accepted; - GSource *source; GTLS_DEBUG(gnutls, "Locking verify_certificate_mutex in verify_certificate_cb"); g_mutex_lock (&priv->verify_certificate_mutex); @@ -1978,13 +1962,11 @@ GTLS_DEBUG(gnutls, "Locking verify_certificate_mutex in verify_certificate_cb"); * necessary because we need to ensure the accept-certificate signal * is emitted on the original thread. */ - source = g_idle_source_new (); - g_source_set_name (source, "[glib-networking] verify_certificate_cb"); - g_source_set_callback (source, accept_certificate_cb, gnutls, NULL); - g_source_set_priority (source, G_PRIORITY_HIGH); - g_source_attach (source, priv->handshake_context); - g_source_unref (source); + g_main_context_invoke (priv->handshake_context, accept_certificate_cb, gnutls); + /* We'll block the handshake thread until the original thread has + * decided whether to accept the certificate. + */ while (!priv->peer_certificate_examined) g_cond_wait (&priv->verify_certificate_condition, &priv->verify_certificate_mutex); accepted = priv->peer_certificate_accepted; @@ -2088,11 +2070,9 @@ handshake_thread (GTask *task, BEGIN_GNUTLS_IO (gnutls, G_IO_IN | G_IO_OUT, timeout, cancellable); ret = gnutls_handshake (priv->session); -GTLS_DEBUG(gnutls, "Finished gnutls_handshake!"); if (ret == GNUTLS_E_GOT_APPLICATION_DATA) { guint8 buf[1024]; -GTLS_DEBUG(gnutls, "GNUTLS_E_GOT_APPLICATION_DATA"); /* Got app data while waiting for rehandshake; buffer it and try again */ ret = gnutls_record_recv (priv->session, buf, sizeof (buf)); @@ -2106,12 +2086,11 @@ GTLS_DEBUG(gnutls, "GNUTLS_E_GOT_APPLICATION_DATA"); } END_GNUTLS_IO (gnutls, G_IO_IN | G_IO_OUT, ret, _("Error performing TLS handshake"), &error); -if (error != NULL) GTLS_DEBUG(gnutls, "error = %s", error->message); + if (!priv->peer_certificate && G_IS_TLS_CLIENT_CONNECTION (gnutls)) { g_set_error_literal (&error, G_TLS_ERROR, G_TLS_ERROR_BAD_CERTIFICATE, _("Server did not return a valid TLS certificate")); -GTLS_DEBUG(gnutls, "Server did not return a valid TLS certificate"); } /* This calls the finish_handshake code of GTlsClientConnectionGnutls @@ -2207,30 +2186,31 @@ sync_handshake_thread_completed (GObject *object, GTlsConnectionGnutls *gnutls = G_TLS_CONNECTION_GNUTLS (object); GTlsConnectionGnutlsPrivate *priv = g_tls_connection_gnutls_get_instance_private (gnutls); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); priv->need_finish_handshake = TRUE; -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); + + g_main_context_wakeup (priv->handshake_context); +GTLS_DEBUG(gnutls, "WAKEUP! need_finish_handshake=TRUE"); } static void -crank_sync_handshake_context (GTlsConnectionGnutls *gnutls) +crank_sync_handshake_context (GTlsConnectionGnutls *gnutls, + GCancellable *cancellable) { GTlsConnectionGnutlsPrivate *priv = g_tls_connection_gnutls_get_instance_private (gnutls); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); priv->need_finish_handshake = FALSE; - while (!priv->need_finish_handshake) +GTLS_DEBUG(gnutls, "%s: need_finish_handshake=FALSE", __FUNCTION__); + while (!priv->need_finish_handshake && !g_cancellable_is_cancelled (cancellable)) { -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); +GTLS_DEBUG(gnutls, "%s: STARTING MAIN CONTEXT=%p ITERATION because need_finish_handshake == FALSE", __FUNCTION__, priv->handshake_context); g_main_context_iteration (priv->handshake_context, TRUE); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); +GTLS_DEBUG(gnutls, "%s: FINISHED MAIN CONTEXT=%p ITERATION", __FUNCTION__, priv->handshake_context); g_mutex_lock (&priv->op_mutex); } -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); } @@ -2246,6 +2226,13 @@ g_tls_connection_gnutls_handshake (GTlsConnection *conn, gint64 *timeout = NULL; GError *my_error = NULL; +GTLS_DEBUG(gnutls, "%s: calling begin_handshake", __FUNCTION__); + + g_assert (priv->handshake_context == NULL); + priv->handshake_context = g_main_context_new (); + + g_main_context_push_thread_default (priv->handshake_context); + begin_handshake (gnutls); task = g_task_new (conn, cancellable, sync_handshake_thread_completed, NULL); @@ -2255,14 +2242,13 @@ g_tls_connection_gnutls_handshake (GTlsConnection *conn, *timeout = -1; /* blocking */ g_task_set_task_data (task, timeout, g_free); - g_assert (priv->handshake_context == NULL); - priv->handshake_context = g_main_context_new (); - g_main_context_push_thread_default (priv->handshake_context); - +GTLS_DEBUG(gnutls, "%s: starting handshake thread and cranking the context", __FUNCTION__); g_task_run_in_thread (task, handshake_thread); - crank_sync_handshake_context (gnutls); + crank_sync_handshake_context (gnutls, cancellable); +GTLS_DEBUG(gnutls, "%s: finished cranking the handshake context", __FUNCTION__); g_main_context_pop_thread_default (priv->handshake_context); + g_clear_pointer (&priv->handshake_context, g_main_context_unref); success = finish_handshake (gnutls, task, &my_error); g_object_unref (task); @@ -2301,7 +2287,6 @@ handshake_thread_completed (GObject *object, g_clear_pointer (&priv->handshake_context, g_main_context_unref); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); if (priv->need_finish_handshake) { @@ -2310,7 +2295,7 @@ GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); } else need_finish_handshake = FALSE; -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); +GTLS_DEBUG(gnutls, "%s: need_finish_handshake=FALSE", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); if (need_finish_handshake) @@ -2339,15 +2324,14 @@ async_handshake_thread (GTask *task, handshake_thread (task, object, task_data, cancellable); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); priv->need_finish_handshake = TRUE; +GTLS_DEBUG(gnutls, "%s: need_finish_handshake=TRUE", __FUNCTION__); /* yield_op will clear handshaking too, but we don't want the * connection to be briefly "handshaking && need_finish_handshake" * after we unlock the mutex. */ priv->handshaking = FALSE; -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); yield_op (gnutls, G_TLS_CONNECTION_GNUTLS_OP_HANDSHAKE); @@ -2364,6 +2348,9 @@ g_tls_connection_gnutls_handshake_async (GTlsConnection *conn, GTask *thread_task, *caller_task; gint64 *timeout = NULL; + g_assert (!priv->handshake_context); + priv->handshake_context = g_main_context_ref_thread_default (); + caller_task = g_task_new (conn, cancellable, callback, user_data); g_task_set_source_tag (caller_task, g_tls_connection_gnutls_handshake_async); g_task_set_priority (caller_task, io_priority); @@ -2379,9 +2366,6 @@ g_tls_connection_gnutls_handshake_async (GTlsConnection *conn, *timeout = -1; /* blocking */ g_task_set_task_data (thread_task, timeout, g_free); - g_assert (!priv->handshake_context); - priv->handshake_context = g_main_context_ref_thread_default (); - g_task_run_in_thread (thread_task, async_handshake_thread); g_object_unref (thread_task); } @@ -2427,6 +2411,17 @@ do_implicit_handshake (GTlsConnectionGnutls *gnutls, /* We have op_mutex */ + g_assert (priv->handshake_context == NULL); + if (timeout != 0) + { + priv->handshake_context = g_main_context_new (); + g_main_context_push_thread_default (priv->handshake_context); + } + else + { + priv->handshake_context = g_main_context_ref_thread_default (); + } + g_assert (priv->implicit_handshake == NULL); priv->implicit_handshake = g_task_new (gnutls, cancellable, timeout ? sync_handshake_thread_completed : NULL, @@ -2452,16 +2447,12 @@ do_implicit_handshake (GTlsConnectionGnutls *gnutls, * operation is complete or errors. */ *thread_timeout = timeout; - g_assert (priv->handshake_context == NULL); - priv->handshake_context = g_main_context_new (); - g_main_context_push_thread_default (priv->handshake_context); - -GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); g_mutex_unlock (&priv->op_mutex); g_task_run_in_thread (priv->implicit_handshake, handshake_thread); - crank_sync_handshake_context (gnutls); + crank_sync_handshake_context (gnutls, cancellable); g_main_context_pop_thread_default (priv->handshake_context); + g_clear_pointer (&priv->handshake_context, g_main_context_unref); success = finish_handshake (gnutls, @@ -2469,7 +2460,6 @@ GTLS_DEBUG(gnutls, "%s: unlocking op_mutex", __FUNCTION__); &my_error); g_clear_object (&priv->implicit_handshake); yield_op (gnutls, G_TLS_CONNECTION_GNUTLS_OP_HANDSHAKE); -GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); g_mutex_lock (&priv->op_mutex); if (my_error) @@ -2484,15 +2474,13 @@ GTLS_DEBUG(gnutls, "%s: locking op_mutex", __FUNCTION__); * about. Run the actual operation as blocking in its thread. */ *thread_timeout = -1; /* blocking */ - g_assert (priv->handshake_context == NULL); - priv->handshake_context = g_main_context_ref_thread_default (); - GTLS_DEBUG(gnutls, "%s: started async_handshake_thread", __FUNCTION__); g_task_run_in_thread (priv->implicit_handshake, async_handshake_thread); g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_WOULD_BLOCK, _("Operation would block")); + return FALSE; } } @@ -2729,14 +2717,10 @@ g_tls_connection_gnutls_write (GTlsConnectionGnutls *gnutls, GTlsConnectionGnutlsPrivate *priv = g_tls_connection_gnutls_get_instance_private (gnutls); gssize ret; again: -GTLS_DEBUG(gnutls, "%s: starting write claim_op, timeout=%" G_GINT64_FORMAT, __FUNCTION__); + if (!claim_op (gnutls, G_TLS_CONNECTION_GNUTLS_OP_WRITE, timeout, cancellable, error)) -{ -GTLS_DEBUG(gnutls, "%s: write claim_op failed, giving up! Oh no!", __FUNCTION__); return -1; -} -GTLS_DEBUG(gnutls, "%s: write claim_op succeeded, starting to write!", __FUNCTION__); BEGIN_GNUTLS_IO (gnutls, G_IO_OUT, timeout, cancellable); ret = gnutls_record_send (priv->session, buffer, count); diff --git a/tls/gnutls/gtlsinputstream-gnutls.c b/tls/gnutls/gtlsinputstream-gnutls.c index df36afd..9128480 100644 --- a/tls/gnutls/gtlsinputstream-gnutls.c +++ b/tls/gnutls/gtlsinputstream-gnutls.c @@ -144,7 +144,6 @@ g_tls_input_stream_gnutls_pollable_read_nonblocking (GPollableInputStream *poll ret = g_tls_connection_gnutls_read (conn, buffer, size, 0 /* non-blocking */, NULL, error); -g_info("%s: ret=%zd", __FUNCTION__, ret); g_object_unref (conn); return ret; |