--- Begin Message ---
Package: release.debian.org
Severity: normal
Tags: buster
User: release.debian....@packages.debian.org
Usertags: pu
Older versions of glib-networking's TLS implementation have a security
issue (CVE-2020-13645): according to the documentation, if the caller
does not specify a server identity, glib-networking should fail closed
(reject all server identities), but in fact it failed open (accept all
server identities).
The only application that was believed to be vulnerable to this
in practice is balsa, which only became vulnerable in post-buster
versions; older versions such as the one in buster implemented their
own TLS. However, if there are other applications in buster that are
vulnerable to this, then they will regress (become unable to connect to
TLS servers) with this update.
The security team have indicated that they would prefer to handle this
via proposed-updates.
Thanks,
smcv
diffstat for glib-networking-2.58.0 glib-networking-2.58.0
changelog | 8
gbp.conf | 4
patches/Return-bad-identity-error-if-identity-is-unset.patch | 158 +++++++++++
patches/debian/01_connection_test.patch | 4
patches/series | 1
5 files changed, 171 insertions(+), 4 deletions(-)
diff -Nru glib-networking-2.58.0/debian/changelog glib-networking-2.58.0/debian/changelog
--- glib-networking-2.58.0/debian/changelog 2018-12-24 14:40:07.000000000 +0000
+++ glib-networking-2.58.0/debian/changelog 2020-07-07 09:30:02.000000000 +0100
@@ -1,3 +1,11 @@
+glib-networking (2.58.0-2+deb10u1) buster; urgency=medium
+
+ * Team upload
+ * d/p/Return-bad-identity-error-if-identity-is-unset.patch:
+ Backport fix for CVE-2020-13645 from upstream (Closes: #961756)
+
+ -- Simon McVittie <s...@debian.org> Tue, 07 Jul 2020 09:30:02 +0100
+
glib-networking (2.58.0-2) unstable; urgency=medium
* Add -Wl,-O1 to our LDFLAGS
diff -Nru glib-networking-2.58.0/debian/gbp.conf glib-networking-2.58.0/debian/gbp.conf
--- glib-networking-2.58.0/debian/gbp.conf 2018-12-24 14:40:07.000000000 +0000
+++ glib-networking-2.58.0/debian/gbp.conf 2020-07-07 09:30:02.000000000 +0100
@@ -1,7 +1,7 @@
[DEFAULT]
pristine-tar = True
-debian-branch = debian/master
-upstream-branch = upstream/latest
+debian-branch = debian/buster
+upstream-branch = upstream/2.58.x
upstream-vcs-tag = %(version)s
[buildpackage]
diff -Nru glib-networking-2.58.0/debian/patches/debian/01_connection_test.patch glib-networking-2.58.0/debian/patches/debian/01_connection_test.patch
--- glib-networking-2.58.0/debian/patches/debian/01_connection_test.patch 2018-12-24 14:40:07.000000000 +0000
+++ glib-networking-2.58.0/debian/patches/debian/01_connection_test.patch 2020-07-07 09:30:02.000000000 +0100
@@ -11,10 +11,10 @@
1 file changed, 2 deletions(-)
diff --git a/tls/tests/meson.build b/tls/tests/meson.build
-index 261fa1e..fb94f22 100644
+index f7489f0..844448a 100644
--- a/tls/tests/meson.build
+++ b/tls/tests/meson.build
-@@ -23,8 +23,6 @@ envs = [
+@@ -25,8 +25,6 @@ envs = [
test_programs = [
['certificate', [], deps],
['file-database', [], deps],
diff -Nru glib-networking-2.58.0/debian/patches/Return-bad-identity-error-if-identity-is-unset.patch glib-networking-2.58.0/debian/patches/Return-bad-identity-error-if-identity-is-unset.patch
--- glib-networking-2.58.0/debian/patches/Return-bad-identity-error-if-identity-is-unset.patch 1970-01-01 01:00:00.000000000 +0100
+++ glib-networking-2.58.0/debian/patches/Return-bad-identity-error-if-identity-is-unset.patch 2020-07-07 09:30:02.000000000 +0100
@@ -0,0 +1,158 @@
+From: Michael Catanzaro <mcatanz...@gnome.org>
+Date: Mon, 4 May 2020 17:47:28 -0500
+Subject: Return bad identity error if identity is unset
+
+When the server-identity property of GTlsClientConnection is unset, the
+documentation sasy we need to fail the certificate verification with
+G_TLS_CERTIFICATE_BAD_IDENTITY. This is important because otherwise,
+it's easy for applications to fail to specify server identity.
+
+Unfortunately, we did not correctly implement the intended, documented
+behavior. When server identity is missing, we check the validity of the
+TLS certificate, but do not check if it corresponds to the expected
+server (since we have no expected server). Then we assume the identity
+is good, instead of returning bad identity, as documented. This means,
+for example, that evil.com can present a valid certificate issued to
+evil.com, and we would happily accept it for paypal.com.
+
+[smcv: Backport to glib-networking 2.58.x, which didn't have OpenSSL
+support or the GTlsConnectionBase base-class]
+
+Bug: https://gitlab.gnome.org/GNOME/glib-networking/-/issues/135
+Origin: backport, 2.62.4, commit:29513946809590c4912550f6f8620468f9836d94
+---
+ tls/gnutls/gtlsconnection-gnutls.c | 20 ++++++-----
+ tls/tests/connection.c | 69 ++++++++++++++++++++++++++++++++++++++
+ 2 files changed, 80 insertions(+), 9 deletions(-)
+
+diff --git a/tls/gnutls/gtlsconnection-gnutls.c b/tls/gnutls/gtlsconnection-gnutls.c
+index 959fa68..3e9f07c 100644
+--- a/tls/gnutls/gtlsconnection-gnutls.c
++++ b/tls/gnutls/gtlsconnection-gnutls.c
+@@ -1736,21 +1736,23 @@ verify_peer_certificate (GTlsConnectionGnutls *gnutls,
+ GTlsCertificate *peer_certificate)
+ {
+ GTlsConnection *conn = G_TLS_CONNECTION (gnutls);
+- GSocketConnectable *peer_identity;
++ GSocketConnectable *peer_identity = NULL;
+ GTlsDatabase *database;
+- GTlsCertificateFlags errors;
++ GTlsCertificateFlags errors = 0;
+ gboolean is_client;
+
+ is_client = G_IS_TLS_CLIENT_CONNECTION (gnutls);
+
+- if (!is_client)
+- peer_identity = NULL;
+- else if (!g_tls_connection_gnutls_is_dtls (gnutls))
+- peer_identity = g_tls_client_connection_get_server_identity (G_TLS_CLIENT_CONNECTION (gnutls));
+- else
+- peer_identity = g_dtls_client_connection_get_server_identity (G_DTLS_CLIENT_CONNECTION (gnutls));
++ if (is_client)
++ {
++ if (!g_tls_connection_gnutls_is_dtls (gnutls))
++ peer_identity = g_tls_client_connection_get_server_identity (G_TLS_CLIENT_CONNECTION (gnutls));
++ else
++ peer_identity = g_dtls_client_connection_get_server_identity (G_DTLS_CLIENT_CONNECTION (gnutls));
+
+- errors = 0;
++ if (!peer_identity)
++ errors |= G_TLS_CERTIFICATE_BAD_IDENTITY;
++ }
+
+ database = g_tls_connection_get_database (conn);
+ if (database == NULL)
+diff --git a/tls/tests/connection.c b/tls/tests/connection.c
+index 6087efc..26dd1ea 100644
+--- a/tls/tests/connection.c
++++ b/tls/tests/connection.c
+@@ -106,6 +106,12 @@ setup_connection (TestConnection *test, gconstpointer data)
+ g_assert (!(var)); \
+ }
+
++static void
++wait_until_server_finished (TestConnection *test)
++{
++ WAIT_UNTIL_UNSET (test->server_running);
++}
++
+ static void
+ teardown_connection (TestConnection *test, gconstpointer data)
+ {
+@@ -1985,6 +1991,67 @@ test_readwrite_after_connection_destroyed (TestConnection *test,
+ g_object_unref (ostream);
+ }
+
++static void
++test_connection_missing_server_identity (TestConnection *test,
++ gconstpointer data)
++{
++ GIOStream *connection;
++ GError *error = NULL;
++
++ test->database = g_tls_file_database_new (tls_test_file_path ("ca-roots.pem"), &error);
++ g_assert_no_error (error);
++ g_assert_nonnull (test->database);
++
++ /* We pass NULL instead of test->identity when creating the client
++ * connection. This means verification must fail with
++ * G_TLS_CERTIFICATE_BAD_IDENTITY.
++ */
++ connection = start_async_server_and_connect_to_it (test, G_TLS_AUTHENTICATION_NONE);
++ test->client_connection = g_tls_client_connection_new (connection, NULL, &error);
++ g_assert_no_error (error);
++ g_assert_nonnull (test->client_connection);
++ g_object_unref (connection);
++
++ g_tls_connection_set_database (G_TLS_CONNECTION (test->client_connection), test->database);
++
++ /* All validation in this test */
++ g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (test->client_connection),
++ G_TLS_CERTIFICATE_VALIDATE_ALL);
++
++ read_test_data_async (test);
++ g_main_loop_run (test->loop);
++ wait_until_server_finished (test);
++
++ g_assert_error (test->read_error, G_TLS_ERROR, G_TLS_ERROR_BAD_CERTIFICATE);
++ //g_assert_error (test->server_error, G_TLS_ERROR, G_TLS_ERROR_NOT_TLS);
++
++ g_clear_error (&test->read_error);
++ g_clear_error (&test->server_error);
++
++ g_clear_object (&test->client_connection);
++ g_clear_object (&test->server_connection);
++
++ /* Now do the same thing again, this time ignoring bad identity. */
++
++ connection = start_async_server_and_connect_to_it (test, G_TLS_AUTHENTICATION_NONE);
++ test->client_connection = g_tls_client_connection_new (connection, NULL, &error);
++ g_assert_no_error (error);
++ g_assert_nonnull (test->client_connection);
++ g_object_unref (connection);
++
++ g_tls_connection_set_database (G_TLS_CONNECTION (test->client_connection), test->database);
++
++ g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (test->client_connection),
++ G_TLS_CERTIFICATE_VALIDATE_ALL & ~G_TLS_CERTIFICATE_BAD_IDENTITY);
++
++ read_test_data_async (test);
++ g_main_loop_run (test->loop);
++ wait_until_server_finished (test);
++
++ g_assert_no_error (test->read_error);
++ g_assert_no_error (test->server_error);
++}
++
+ int
+ main (int argc,
+ char *argv[])
+@@ -2055,6 +2122,8 @@ main (int argc,
+ setup_connection, test_garbage_database, teardown_connection);
+ g_test_add ("/tls/connection/readwrite-after-connection-destroyed", TestConnection, NULL,
+ setup_connection, test_readwrite_after_connection_destroyed, teardown_connection);
++ g_test_add ("/tls/connection/missing-server-identity", TestConnection, NULL,
++ setup_connection, test_connection_missing_server_identity, teardown_connection);
+
+ ret = g_test_run ();
+
diff -Nru glib-networking-2.58.0/debian/patches/series glib-networking-2.58.0/debian/patches/series
--- glib-networking-2.58.0/debian/patches/series 2018-12-24 14:40:07.000000000 +0000
+++ glib-networking-2.58.0/debian/patches/series 2020-07-07 09:30:02.000000000 +0100
@@ -1 +1,2 @@
+Return-bad-identity-error-if-identity-is-unset.patch
debian/01_connection_test.patch
--- End Message ---