--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/tls/gnutls/gtlsserverconnection-gnutls.c	2011-09-27 00:02:48.000000000 +0200
+++ GLIB-NETWORKING/glib-networking-2.30.90/tls/gnutls/gtlsserverconnection-gnutls.c	2012-02-29 15:20:22.487417290 +0100
@@ -29,6 +29,8 @@
 #include "gtlscertificate-gnutls.h"
 #include <glib/gi18n-lib.h>
 
+#define MAX_SERVER_NAME_LEN 255
+
 enum
 {
   PROP_0,
@@ -167,7 +169,10 @@
     }
 
   session = g_tls_connection_gnutls_get_session (conn);
+	gnutls_handshake_set_post_client_hello_function(session, g_tls_server_connection_gnutls_server_name_cb); 
+
   gnutls_certificate_server_set_request (session, req_mode);
+
 }
 
 static gboolean
@@ -203,9 +208,45 @@
                                                    peer_certificate, *errors);
 }
 
+
 static void
 g_tls_server_connection_gnutls_finish_handshake (GTlsConnectionGnutls  *gnutls,
 						 gboolean               success,
 						 GError               **inout_error)
 {
 }
+
+static int 
+g_tls_server_connection_gnutls_server_name_cb(gnutls_session_t session) {
+  gchar   server_name[MAX_SERVER_NAME_LEN];
+  size_t  server_name_length = MAX_SERVER_NAME_LEN;
+	unsigned int server_name_type;
+	
+  switch(gnutls_server_name_get(session, server_name, &server_name_length, &server_name_type, 0)) {
+    case GNUTLS_E_SUCCESS:
+      if(server_name_type == GNUTLS_NAME_DNS) {
+        if(g_tls_server_connection_emit_received_server_identity (G_TLS_CONNECTION (gnutls_transport_get_ptr (session)), server_name) == TRUE) {
+          return GNUTLS_E_SUCCESS;
+        } else {
+          return GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE;
+        }
+
+      } else {
+        g_warning("TLS Server Name Indication extension failure: unknown data type");
+        return GNUTLS_E_SUCCESS;
+      }
+      
+    case GNUTLS_E_SHORT_MEMORY_BUFFER:
+      g_warning("TLS Server Name Indication extension failure: memory buffer was too short to contain the server name");
+      return GNUTLS_E_SHORT_MEMORY_BUFFER;
+
+    case GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE:
+      if(g_tls_server_connection_emit_received_server_identity (G_TLS_CONNECTION (gnutls_transport_get_ptr (session)), NULL) == TRUE) {
+        return GNUTLS_E_SUCCESS;
+      } else {
+        return GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE;
+      }
+
+  }
+}
+
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/tls/gnutls/gtlsserverconnection-gnutls.h	2010-11-29 19:35:14.000000000 +0100
+++ GLIB-NETWORKING/glib-networking-2.30.90/tls/gnutls/gtlsserverconnection-gnutls.h	2012-02-29 15:19:20.000000000 +0100
@@ -44,4 +44,6 @@
 
 G_END_DECLS
 
+static int g_tls_server_connection_gnutls_server_name_cb(gnutls_session_t session);
+
 #endif /* __G_TLS_SERVER_CONNECTION_GNUTLS_H___ */
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/tls/tests/tls.c	2011-09-27 00:02:48.000000000 +0200
+++ GLIB-NETWORKING/glib-networking-2.30.90/tls/tests/tls.c	2012-02-29 15:19:20.000000000 +0100
@@ -45,6 +45,7 @@
   GTlsAuthenticationMode auth_mode;
   gboolean rehandshake;
   GTlsCertificateFlags accept_flags;
+  gboolean switch_cert_to_other;
 } TestConnection;
 
 static void
@@ -65,6 +66,9 @@
 
   /* The identity matches the server certificate */
   test->identity = g_network_address_new ("server.example.com", port);
+
+  /* Do not try to switch certificate to other.example.com when server name indication is requested */
+  test->switch_cert_to_other = FALSE;
 }
 
 static void
@@ -179,6 +183,42 @@
                                on_output_close_finish, test);
 }
 
+static gboolean 
+on_received_server_identity (GTlsConnection *connection, 
+                             gchar          *identity,
+                             gpointer        user_data)
+{
+  TestConnection *test = user_data;
+  GTlsCertificate *cert;
+  GError *error = NULL;
+  gchar *path;
+
+  if(test->switch_cert_to_other) {
+    if(identity != NULL) {
+      printf("Got received-server-identity signal with identity \"%s\"\n", identity);
+      
+      if(g_strcmp0(identity, "other.example.com") == 0) {
+        printf("Trying to load certificate for other.example.com\n");
+
+        path = g_build_filename (source_dir, "other-server-and-key.pem", NULL);
+        cert = g_tls_certificate_new_from_file (path, &error);
+        g_assert_no_error (error);
+        g_free (path);
+        
+        g_tls_connection_set_certificate (connection, cert);
+        g_object_unref (cert);
+      }
+
+      
+    } else {
+      printf("Got received-server-identity signal with no identity\n");
+    }
+  }
+  
+  return TRUE;
+}
+
+
 static gboolean
 on_incoming_connection (GSocketService     *service,
                         GSocketConnection  *connection,
@@ -201,9 +241,12 @@
   g_assert_no_error (error);
   g_object_unref (cert);
 
+
   g_object_set (test->server_connection, "authentication-mode", test->auth_mode, NULL);
   g_signal_connect (test->server_connection, "accept-certificate",
                     G_CALLBACK (on_accept_certificate), test);
+  g_signal_connect (test->server_connection, "received-server-identity", 
+                    G_CALLBACK (on_received_server_identity), test);
 
   if (test->database)
     g_tls_connection_set_database (G_TLS_CONNECTION (test->server_connection), test->database);
@@ -308,6 +351,56 @@
 }
 
 static void
+test_basic_connection_with_other_server_name (TestConnection *test,
+                       gconstpointer   data)
+{
+  GIOStream *connection;
+  GError *error = NULL;
+
+  connection = start_server_and_connect_to_it (test, G_TLS_AUTHENTICATION_NONE);
+
+  test->identity = g_network_address_new ("other.example.com", 80);
+
+  test->client_connection = g_tls_client_connection_new (connection, test->identity, &error);
+  g_assert_no_error (error);
+  g_object_unref (connection);
+
+  /* No validation at all in this test */
+  g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (test->client_connection),
+                                                0);
+
+  read_test_data_async (test);
+  g_main_loop_run (test->loop);
+}
+
+
+
+static void
+test_basic_connection_with_other_server_name_and_identity_validation (TestConnection *test,
+                       gconstpointer   data)
+{
+  GIOStream *connection;
+  GError *error = NULL;
+
+  connection = start_server_and_connect_to_it (test, G_TLS_AUTHENTICATION_NONE);
+
+  test->identity = g_network_address_new ("other.example.com", 80);
+  test->switch_cert_to_other = TRUE;
+
+  test->client_connection = g_tls_client_connection_new (connection, test->identity, &error);
+  g_assert_no_error (error);
+  g_object_unref (connection);
+
+  /* Do not validate CA in this test */  // FIXME - regenerate test certificate with proper CA
+  g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (test->client_connection),
+                                                G_TLS_CERTIFICATE_VALIDATE_ALL & ~G_TLS_CERTIFICATE_UNKNOWN_CA); 
+
+
+  read_test_data_async (test);
+  g_main_loop_run (test->loop);
+}
+
+static void
 test_verified_connection (TestConnection *test,
                           gconstpointer   data)
 {
@@ -1106,6 +1199,10 @@
 
   g_test_add ("/tls/connection/basic", TestConnection, NULL,
               setup_connection, test_basic_connection, teardown_connection);
+  g_test_add ("/tls/connection/basic (with other server name, no validation)", TestConnection, NULL,
+              setup_connection, test_basic_connection_with_other_server_name, teardown_connection);
+  g_test_add ("/tls/connection/basic (with other server name & identity validation)", TestConnection, NULL,
+              setup_connection, test_basic_connection_with_other_server_name_and_identity_validation, teardown_connection);
   g_test_add ("/tls/connection/verified", TestConnection, NULL,
               setup_connection, test_verified_connection, teardown_connection);
   g_test_add ("/tls/connection/client-auth", TestConnection, NULL,
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/debian/control.in	2011-09-21 14:41:57.000000000 +0200
+++ GLIB-NETWORKING/glib-networking-2.30.90/debian/control.in	2012-02-29 15:25:16.044872901 +0100
@@ -7,7 +7,7 @@
 Build-Depends: debhelper (>= 8),
                cdbs,
                gnome-pkg-tools,
-               libglib2.0-dev (>= 2.29.18),
+               libglib2.0-dev (>= 2.30.90),
                libgnutls-dev (>= 2.1.7),
                libproxy-dev (>= 0.3.1),
                gsettings-desktop-schemas-dev,
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/tls/tests/files/other-server-and-key.pem	2012-02-29 15:32:08.698919242 +0100
+++ GLIB-NETWORKING/glib-networking-2.30.90/tls/tests/files/other-server-and-key.pem	2012-02-29 15:19:20.000000000 +0100
@@ -0,0 +1,29 @@
+-----BEGIN CERTIFICATE-----
+MIICOTCCAaICCQD6mMuolL4XwTANBgkqhkiG9w0BAQUFADBhMQswCQYDVQQGEwJB
+VTETMBEGA1UECAwKU29tZS1TdGF0ZTEhMB8GA1UECgwYSW50ZXJuZXQgV2lkZ2l0
+cyBQdHkgTHRkMRowGAYDVQQDDBFvdGhlci5leGFtcGxlLmNvbTAeFw0xMjAyMjkx
+MzUzMDlaFw0yMjAyMjYxMzUzMDlaMGExCzAJBgNVBAYTAkFVMRMwEQYDVQQIDApT
+b21lLVN0YXRlMSEwHwYDVQQKDBhJbnRlcm5ldCBXaWRnaXRzIFB0eSBMdGQxGjAY
+BgNVBAMMEW90aGVyLmV4YW1wbGUuY29tMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCB
+iQKBgQDIc5RtBtJL6+SGvu0+VFJXuOotW9zpPYM8Jsf0o3SF1G1tg1IBFziL1yPF
+x0v9lalOHzXa9PtcJvVEfbMOsmLjIeRK1E9JMl3HFkqDeiskbOcUzG8xG0MDgcRP
+qh5IAdR2yNTEalkJzHWHPMmgmPMQTZf7tqsEBoBDrXyHnmDmNwIDAQABMA0GCSqG
+SIb3DQEBBQUAA4GBAIroJ7/yXs2FrsGo3EdB2Iz5WK2UeyQYNVmyXifNp6vIq53P
+eruBeE4cy82/lNVJNLU+C2I/yNnf9w1tZLhUoc0D0Kk88LUo7upYvJrbPo/xzBCI
+7QIzqPsQNF89DtKJaddopAYiHedI9vRg2YsbPBec7Pi0YFtiBP/vA1xNG8M/
+-----END CERTIFICATE-----
+-----BEGIN RSA PRIVATE KEY-----
+MIICXQIBAAKBgQDIc5RtBtJL6+SGvu0+VFJXuOotW9zpPYM8Jsf0o3SF1G1tg1IB
+FziL1yPFx0v9lalOHzXa9PtcJvVEfbMOsmLjIeRK1E9JMl3HFkqDeiskbOcUzG8x
+G0MDgcRPqh5IAdR2yNTEalkJzHWHPMmgmPMQTZf7tqsEBoBDrXyHnmDmNwIDAQAB
+AoGBALv5t0zuwrMzyaCa1zxGMtnUrLZQmT+Y0cLM02KVDiaaaOvz5Cjlr79jx0Yn
+eRmbCaQbHJPyfO2UExlhj1LO8m9G9YZatJN3O5dSZ+ITADMF5R0QSHOoa+nYxzE3
+ORKi6W74/hI3JWSdS79r9l965B16FUpYRddFN/zSKYBXXvHxAkEA9kNbxv8wYSjt
+U++o3vGHL9jJ9W6WQetINnDW3Ap5s7czRR4MFnA8e/NRlVQf/kTiIWcPb2pP3rfn
+swNy877f3QJBANBgha6R8ZAWeU/94RFDq2RtU8Gk22SjEzlTtqj+0AeZ8cDbsAAJ
+HDaoB2K0elerGs+QpsaIBsKXI+Tra43aRyMCQB0l2d4S5FoLqxONQVKqCdM6+KSJ
+I1XIEHMJJhVDVCZWX8YliU66mB4frZ9cJrFE2/MSLLyGO8/jupPwq5F4HS0CQQCZ
+35z4A0eZei8NFdH8mLbYyy69YUqtbwrEG4BYHQprgo+WNeQqso+GAOCrT9DEKlL7
+EbtGAa7URR25busWbih3AkBshLPsBaWWrxZV8zx6+6BZiK9NiGbaHwjVPEyd4Ddx
+h0m7iFD0lZCrabghuggd9XFUKXqSD3CAiA5CVeav/aRg
+-----END RSA PRIVATE KEY-----
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/configure.ac	2011-09-27 00:03:05.000000000 +0200
+++ GLIB-NETWORKING/glib-networking-2.30.90/configure.ac	2012-02-29 15:39:37.161143012 +0100
@@ -1,7 +1,7 @@
 AC_PREREQ(2.65)
 AC_CONFIG_MACRO_DIR([m4])
 
-AC_INIT([glib-networking],[2.30.0],[http://bugzilla.gnome.org/enter_bug.cgi?product=glib&component=network])
+AC_INIT([glib-networking],[2.30.90],[http://bugzilla.gnome.org/enter_bug.cgi?product=glib&component=network])
 
 AC_CONFIG_SRCDIR([proxy/libproxy/glibproxyresolver.h])
 AC_CONFIG_HEADERS([config.h])
@@ -33,7 +33,7 @@
 dnl *****************************
 dnl *** Check GLib GIO        ***
 dnl *****************************
-AM_PATH_GLIB_2_0(2.29.18,,AC_MSG_ERROR(GLIB not found),gio)
+AM_PATH_GLIB_2_0(2.30.90,,AC_MSG_ERROR(GLIB not found),gio)
 
 GIO_MODULE_DIR=$($PKG_CONFIG --variable giomoduledir gio-2.0)
 AS_IF([test "x$GIO_MODULE_DIR" = "x"],
--- GLIB-NETWORKING-CLEAN/glib-networking-2.30.0/debian/changelog	2011-09-28 16:36:07.000000000 +0200
+++ GLIB-NETWORKING/glib-networking-2.30.90/debian/changelog	2012-02-29 15:21:44.955826248 +0100
@@ -1,3 +1,9 @@
+glib-networking (2.30.90-0ubuntu1) oneiric; urgency=low
+
+  * Patched to support TLS Server Name Indication
+
+ -- Marcin Lewandowski <marcin.lewandowski@svada.pl>  Wed, 29 Feb 2012 15:20:59 +0100
+
 glib-networking (2.30.0-0ubuntu1) oneiric; urgency=low
 
   * New upstream release: Just translation updates.
