File nm-applet-probe-radius-server-cert.patch of Package NetworkManager-gnome

From 2f3604bd386ab8016caa54b5de024fec74c55817 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <chingpang@gmail.com>
Date: Wed, 18 Jul 2012 14:52:29 +0800
Subject: [PATCH 1/5] security: new entry for the subject and support server
 hash

---
 src/wireless-security/eap-method-peap.c   | 86 +++++++++++++++++++++++++++++++
 src/wireless-security/eap-method-peap.ui  | 70 +++++++++++++++++++------
 src/wireless-security/eap-method-tls.c    | 73 ++++++++++++++++++++++++++
 src/wireless-security/eap-method-tls.ui   | 59 +++++++++++++++------
 src/wireless-security/eap-method-ttls.c   | 86 +++++++++++++++++++++++++++++++
 src/wireless-security/eap-method-ttls.ui  | 62 ++++++++++++++++++----
 src/wireless-security/wireless-security.c | 22 ++++++++
 src/wireless-security/wireless-security.h |  3 ++
 8 files changed, 420 insertions(+), 41 deletions(-)

diff --git a/src/wireless-security/eap-method-peap.c b/src/wireless-security/eap-method-peap.c
index 4d2041c..5f58804 100644
--- a/src/wireless-security/eap-method-peap.c
+++ b/src/wireless-security/eap-method-peap.c
@@ -35,6 +35,8 @@
 #define I_NAME_COLUMN   0
 #define I_METHOD_COLUMN 1
 
+#define SUBJECT_NOTE _("<will be filled automatically>")
+
 struct _EAPMethodPEAP {
 	EAPMethod parent;
 
@@ -93,6 +95,10 @@ add_to_size_group (EAPMethod *parent, GtkSizeGroup *group)
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_subject_label"));
+	g_assert (widget);
+	gtk_size_group_add_widget (group, widget);
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_ca_cert_label"));
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
@@ -141,6 +147,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 	if (text && strlen (text))
 		g_object_set (s_8021x, NM_SETTING_802_1X_ANONYMOUS_IDENTITY, text, NULL);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_subject_entry"));
+	g_assert (widget);
+	text = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (text && strlen (text)  && g_strcmp0 (text, SUBJECT_NOTE) != 0)
+		g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, text, NULL);
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_ca_cert_button"));
 	g_assert (widget);
 	filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (widget));
@@ -308,6 +320,37 @@ update_secrets (EAPMethod *parent, NMConnection *connection)
 	                                         I_METHOD_COLUMN);
 }
 
+static gboolean
+subject_entry_focus_in_cb (GtkWidget *widget,
+                           GdkEvent  *event,
+                           gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (g_strcmp0 (text, SUBJECT_NOTE) == 0) {
+		gtk_entry_set_text (GTK_ENTRY (widget), "");
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, NULL);
+	}
+	return FALSE;
+}
+
+static gboolean
+subject_entry_focus_out_cb (GtkWidget *widget,
+                            GdkEvent  *event,
+                            gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	GtkStyleContext *context;
+	GdkRGBA color;
+
+	if (!text || !strlen (text)) {
+		gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		context = gtk_widget_get_style_context (widget);
+		gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+	}
+	return FALSE;
+}
+
 EAPMethodPEAP *
 eap_method_peap_new (WirelessSecurity *ws_parent,
                      NMConnection *connection,
@@ -383,6 +426,43 @@ eap_method_peap_new (WirelessSecurity *ws_parent,
 	                  (GCallback) wireless_security_changed_cb,
 	                  ws_parent);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_subject_entry"));
+	if (s_8021x) {
+		const char *text = nm_setting_802_1x_get_subject_match (s_8021x);
+		if (!text) {
+			GtkStyleContext *context;
+			GdkRGBA color;
+			context = gtk_widget_get_style_context (widget);
+			gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+			gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+			gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		} else {
+			gtk_entry_set_text (GTK_ENTRY (widget), text);
+		}
+		g_signal_connect (G_OBJECT (widget), "focus-in-event",
+		                  (GCallback) subject_entry_focus_in_cb,
+		                  NULL);
+		g_signal_connect (G_OBJECT (widget), "focus-out-event",
+		                  (GCallback) subject_entry_focus_out_cb,
+		                  NULL);
+	}
+	g_signal_connect (G_OBJECT (widget), "changed",
+	                  (GCallback) wireless_security_changed_cb,
+	                  ws_parent);
+
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_note_label"));
+	if (s_8021x) {
+		NMSetting8021xCKScheme cert_scheme;
+		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+		if (cert_scheme == NM_SETTING_802_1X_CK_SCHEME_HASH) {
+			gtk_label_set_text (GTK_LABEL (widget),
+			                    _("<b>Note:</b> Server hash is used instead of CA certificate"));
+			gtk_label_set_use_markup (GTK_LABEL (widget), TRUE);
+		} else {
+			gtk_widget_hide (widget);
+		}
+	}
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_anon_identity_entry"));
 	if (s_8021x && nm_setting_802_1x_get_anonymous_identity (s_8021x))
 		gtk_entry_set_text (GTK_ENTRY (widget), nm_setting_802_1x_get_anonymous_identity (s_8021x));
@@ -395,10 +475,16 @@ eap_method_peap_new (WirelessSecurity *ws_parent,
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_anon_identity_entry"));
 		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_subject_label"));
+		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_subject_entry"));
+		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_ca_cert_label"));
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_ca_cert_button"));
 		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_note_label"));
+		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_inner_auth_label"));
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_inner_auth_combo"));
diff --git a/src/wireless-security/eap-method-peap.ui b/src/wireless-security/eap-method-peap.ui
index dcfa9d5..755a8d6 100644
--- a/src/wireless-security/eap-method-peap.ui
+++ b/src/wireless-security/eap-method-peap.ui
@@ -35,7 +35,7 @@
         <child>
           <object class="GtkTable" id="table13">
             <property name="visible">True</property>
-            <property name="n_rows">5</property>
+            <property name="n_rows">7</property>
             <property name="n_columns">2</property>
             <property name="column_spacing">12</property>
             <property name="row_spacing">6</property>
@@ -65,6 +65,35 @@
               </packing>
             </child>
             <child>
+              <object class="GtkLabel" id="eap_peap_subject_label">
+                <property name="visible">True</property>
+                <property name="xalign">0</property>
+                <property name="label" translatable="yes">_Subject:</property>
+                <property name="use_underline">True</property>
+                <property name="mnemonic_widget">eap_peap_subject_entry</property>
+              </object>
+              <packing>
+                <property name="top_attach">1</property>
+                <property name="bottom_attach">2</property>
+                <property name="x_options">GTK_FILL</property>
+                <property name="y_options"></property>
+              </packing>
+            </child>
+            <child>
+              <object class="GtkEntry" id="eap_peap_subject_entry">
+                <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="activates_default">True</property>
+              </object>
+              <packing>
+                <property name="left_attach">1</property>
+                <property name="right_attach">2</property>
+                <property name="top_attach">1</property>
+                <property name="bottom_attach">2</property>
+                <property name="y_options"></property>
+              </packing>
+            </child>
+            <child>
               <object class="GtkLabel" id="eap_peap_ca_cert_label">
                 <property name="visible">True</property>
                 <property name="xalign">0</property>
@@ -73,8 +102,8 @@
                 <property name="mnemonic_widget">eap_peap_ca_cert_button</property>
               </object>
               <packing>
-                <property name="top_attach">1</property>
-                <property name="bottom_attach">2</property>
+                <property name="top_attach">2</property>
+                <property name="bottom_attach">3</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -86,13 +115,24 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">1</property>
-                <property name="bottom_attach">2</property>
+                <property name="top_attach">2</property>
+                <property name="bottom_attach">3</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
             </child>
             <child>
+              <object class="GtkLabel" id="eap_peap_note_label">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Note</property>
+              </object>
+              <packing>
+                <property name="right_attach">2</property>
+                <property name="top_attach">3</property>
+                <property name="bottom_attach">4</property>
+              </packing>
+            </child>
+            <child>
               <object class="GtkVBox" id="eap_peap_inner_auth_vbox">
                 <property name="visible">True</property>
                 <property name="orientation">vertical</property>
@@ -102,8 +142,8 @@
               </object>
               <packing>
                 <property name="right_attach">2</property>
-                <property name="top_attach">4</property>
-                <property name="bottom_attach">5</property>
+                <property name="top_attach">6</property>
+                <property name="bottom_attach">7</property>
                 <property name="x_options">GTK_FILL</property>
               </packing>
             </child>
@@ -116,8 +156,8 @@
                 <property name="mnemonic_widget">eap_peap_inner_auth_combo</property>
               </object>
               <packing>
-                <property name="top_attach">3</property>
-                <property name="bottom_attach">4</property>
+                <property name="top_attach">5</property>
+                <property name="bottom_attach">6</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -136,8 +176,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">3</property>
-                <property name="bottom_attach">4</property>
+                <property name="top_attach">5</property>
+                <property name="bottom_attach">6</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
@@ -151,8 +191,8 @@
                 <property name="mnemonic_widget">eap_peap_version_combo</property>
               </object>
               <packing>
-                <property name="top_attach">2</property>
-                <property name="bottom_attach">3</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -171,8 +211,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">2</property>
-                <property name="bottom_attach">3</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
diff --git a/src/wireless-security/eap-method-tls.c b/src/wireless-security/eap-method-tls.c
index da02873..22e53d0 100644
--- a/src/wireless-security/eap-method-tls.c
+++ b/src/wireless-security/eap-method-tls.c
@@ -33,6 +33,8 @@
 #include "wireless-security.h"
 #include "helpers.h"
 
+#define SUBJECT_NOTE _("<will be filled automatically>")
+
 struct _EAPMethodTLS {
 	EAPMethod parent;
 
@@ -107,6 +109,10 @@ add_to_size_group (EAPMethod *parent, GtkSizeGroup *group)
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_subject_label"));
+	g_assert (widget);
+	gtk_size_group_add_widget (group, widget);
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_private_key_label"));
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
@@ -124,6 +130,7 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 	NMSetting8021x *s_8021x;
 	GtkWidget *widget;
 	char *ca_filename, *pk_filename, *cc_filename;
+	const char *subject;
 	const char *password = NULL;
 	GError *error = NULL;
 	const char *secret_flag_prop = NULL;
@@ -216,6 +223,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 			g_clear_error (&error);
 		}
 	}
+
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_subject_entry"));
+	g_assert (widget);
+	subject = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (subject && strlen (subject)  && g_strcmp0 (subject, SUBJECT_NOTE) != 0)
+		g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, subject, NULL);
 }
 
 static void
@@ -384,6 +397,37 @@ update_secrets (EAPMethod *parent, NMConnection *connection)
 	}
 }
 
+static gboolean
+subject_entry_focus_in_cb (GtkWidget *widget,
+                           GdkEvent  *event,
+                           gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (g_strcmp0 (text, SUBJECT_NOTE) == 0) {
+		gtk_entry_set_text (GTK_ENTRY (widget), "");
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, NULL);
+	}
+	return FALSE;
+}
+
+static gboolean
+subject_entry_focus_out_cb (GtkWidget *widget,
+                            GdkEvent  *event,
+                            gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	GtkStyleContext *context;
+	GdkRGBA color;
+
+	if (!text || !strlen (text)) {
+		gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		context = gtk_widget_get_style_context (widget);
+		gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+	}
+	return FALSE;
+}
+
 EAPMethodTLS *
 eap_method_tls_new (WirelessSecurity *ws_parent,
                     NMConnection *connection,
@@ -436,6 +480,31 @@ eap_method_tls_new (WirelessSecurity *ws_parent,
 	                  phase2 ? nm_setting_802_1x_get_phase2_ca_cert_scheme : nm_setting_802_1x_get_ca_cert_scheme,
 	                  phase2 ? nm_setting_802_1x_get_phase2_ca_cert_path : nm_setting_802_1x_get_ca_cert_path,
 	                  FALSE, FALSE);
+
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_subject_entry"));
+	if (s_8021x) {
+		const char *text = nm_setting_802_1x_get_subject_match (s_8021x);
+		if (!text) {
+			GtkStyleContext *context;
+			GdkRGBA color;
+			context = gtk_widget_get_style_context (widget);
+			gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+			gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+			gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		} else {
+			gtk_entry_set_text (GTK_ENTRY (widget), text);
+		}
+		g_signal_connect (G_OBJECT (widget), "focus-in-event",
+		                  (GCallback) subject_entry_focus_in_cb,
+		                  NULL);
+		g_signal_connect (G_OBJECT (widget), "focus-out-event",
+		                  (GCallback) subject_entry_focus_out_cb,
+		                  NULL);
+	}
+	g_signal_connect (G_OBJECT (widget), "changed",
+	                  (GCallback) wireless_security_changed_cb,
+	                  ws_parent);
+
 	setup_filepicker (parent->builder, "eap_tls_private_key_button",
 	                  _("Choose your private key..."),
 	                  ws_parent, parent, s_8021x,
@@ -474,6 +543,10 @@ eap_method_tls_new (WirelessSecurity *ws_parent,
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_ca_cert_button"));
 		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_subject_label"));
+		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_tls_subject_entry"));
+		gtk_widget_hide (widget);
 	}
 
 	return method;
diff --git a/src/wireless-security/eap-method-tls.ui b/src/wireless-security/eap-method-tls.ui
index a643965..a46edb8 100644
--- a/src/wireless-security/eap-method-tls.ui
+++ b/src/wireless-security/eap-method-tls.ui
@@ -9,7 +9,7 @@
         <child>
           <object class="GtkTable" id="table8">
             <property name="visible">True</property>
-            <property name="n_rows">6</property>
+            <property name="n_rows">7</property>
             <property name="n_columns">2</property>
             <property name="column_spacing">12</property>
             <property name="row_spacing">6</property>
@@ -54,12 +54,12 @@
               </packing>
             </child>
             <child>
-              <object class="GtkLabel" id="eap_tls_ca_cert_label">
+              <object class="GtkLabel" id="eap_tls_subject_label">
                 <property name="visible">True</property>
                 <property name="xalign">0</property>
-                <property name="label" translatable="yes">C_A certificate:</property>
+                <property name="label" translatable="yes">CA _subject:</property>
                 <property name="use_underline">True</property>
-                <property name="mnemonic_widget">eap_tls_ca_cert_button</property>
+                <property name="mnemonic_widget">eap_tls_subject_entry</property>
               </object>
               <packing>
                 <property name="top_attach">2</property>
@@ -69,14 +69,43 @@
               </packing>
             </child>
             <child>
-              <object class="GtkFileChooserButton" id="eap_tls_ca_cert_button">
+              <object class="GtkEntry" id="eap_tls_subject_entry">
                 <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="activates_default">True</property>
               </object>
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
                 <property name="top_attach">2</property>
                 <property name="bottom_attach">3</property>
+                <property name="y_options"/>
+              </packing>
+            </child>
+            <child>
+              <object class="GtkLabel" id="eap_tls_ca_cert_label">
+                <property name="visible">True</property>
+                <property name="xalign">0</property>
+                <property name="label" translatable="yes">C_A certificate:</property>
+                <property name="use_underline">True</property>
+                <property name="mnemonic_widget">eap_tls_ca_cert_button</property>
+              </object>
+              <packing>
+                <property name="top_attach">3</property>
+                <property name="bottom_attach">4</property>
+                <property name="x_options">GTK_FILL</property>
+                <property name="y_options"/>
+              </packing>
+            </child>
+            <child>
+              <object class="GtkFileChooserButton" id="eap_tls_ca_cert_button">
+                <property name="visible">True</property>
+              </object>
+              <packing>
+                <property name="left_attach">1</property>
+                <property name="right_attach">2</property>
+                <property name="top_attach">3</property>
+                <property name="bottom_attach">4</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
@@ -90,8 +119,8 @@
                 <property name="mnemonic_widget">eap_tls_private_key_button</property>
               </object>
               <packing>
-                <property name="top_attach">3</property>
-                <property name="bottom_attach">4</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -103,8 +132,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">3</property>
-                <property name="bottom_attach">4</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
@@ -118,8 +147,8 @@
                 <property name="mnemonic_widget">eap_tls_private_key_password_entry</property>
               </object>
               <packing>
-                <property name="top_attach">4</property>
-                <property name="bottom_attach">5</property>
+                <property name="top_attach">5</property>
+                <property name="bottom_attach">6</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -134,8 +163,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">4</property>
-                <property name="bottom_attach">5</property>
+                <property name="top_attach">5</property>
+                <property name="bottom_attach">6</property>
                 <property name="y_options"/>
               </packing>
             </child>
@@ -151,8 +180,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">5</property>
-                <property name="bottom_attach">6</property>
+                <property name="top_attach">6</property>
+                <property name="bottom_attach">7</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
diff --git a/src/wireless-security/eap-method-ttls.c b/src/wireless-security/eap-method-ttls.c
index 65346c2..1fe8431 100644
--- a/src/wireless-security/eap-method-ttls.c
+++ b/src/wireless-security/eap-method-ttls.c
@@ -35,6 +35,8 @@
 #define I_NAME_COLUMN   0
 #define I_METHOD_COLUMN 1
 
+#define SUBJECT_NOTE _("<will be filled automatically>")
+
 struct _EAPMethodTTLS {
 	EAPMethod parent;
 
@@ -93,6 +95,10 @@ add_to_size_group (EAPMethod *parent, GtkSizeGroup *group)
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_subject_label"));
+	g_assert (widget);
+	gtk_size_group_add_widget (group, widget);
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_ca_cert_label"));
 	g_assert (widget);
 	gtk_size_group_add_widget (group, widget);
@@ -136,6 +142,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 	if (text && strlen (text))
 		g_object_set (s_8021x, NM_SETTING_802_1X_ANONYMOUS_IDENTITY, text, NULL);
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_subject_entry"));
+	g_assert (widget);
+	text = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (text && strlen (text)  && g_strcmp0 (text, SUBJECT_NOTE) != 0)
+		g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, text, NULL);
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_ca_cert_button"));
 	g_assert (widget);
 	filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (widget));
@@ -308,6 +320,37 @@ update_secrets (EAPMethod *parent, NMConnection *connection)
 	                                         I_METHOD_COLUMN);
 }
 
+static gboolean
+subject_entry_focus_in_cb (GtkWidget *widget,
+                           GdkEvent  *event,
+                           gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	if (g_strcmp0 (text, SUBJECT_NOTE) == 0) {
+		gtk_entry_set_text (GTK_ENTRY (widget), "");
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, NULL);
+	}
+	return FALSE;
+}
+
+static gboolean
+subject_entry_focus_out_cb (GtkWidget *widget,
+                            GdkEvent  *event,
+                            gpointer user_data)
+{
+	const char *text = gtk_entry_get_text (GTK_ENTRY (widget));
+	GtkStyleContext *context;
+	GdkRGBA color;
+
+	if (!text || !strlen (text)) {
+		gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		context = gtk_widget_get_style_context (widget);
+		gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+		gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+	}
+	return FALSE;
+}
+
 EAPMethodTTLS *
 eap_method_ttls_new (WirelessSecurity *ws_parent,
                      NMConnection *connection,
@@ -361,6 +404,43 @@ eap_method_ttls_new (WirelessSecurity *ws_parent,
 		}
 	}
 
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_subject_entry"));
+	if (s_8021x) {
+		const char *text = nm_setting_802_1x_get_subject_match (s_8021x);
+		if (!text) {
+			GtkStyleContext *context;
+			GdkRGBA color;
+			context = gtk_widget_get_style_context (widget);
+			gtk_style_context_get_color (context, GTK_STATE_FLAG_INSENSITIVE, &color);
+			gtk_widget_override_color (widget, GTK_STATE_FLAG_NORMAL, &color);
+			gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE);
+		} else {
+			gtk_entry_set_text (GTK_ENTRY (widget), text);
+		}
+		g_signal_connect (G_OBJECT (widget), "focus-in-event",
+		                  (GCallback) subject_entry_focus_in_cb,
+		                  NULL);
+		g_signal_connect (G_OBJECT (widget), "focus-out-event",
+		                  (GCallback) subject_entry_focus_out_cb,
+		                  NULL);
+	}
+	g_signal_connect (G_OBJECT (widget), "changed",
+	                  (GCallback) wireless_security_changed_cb,
+	                  ws_parent);
+
+	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_note_label"));
+	if (s_8021x) {
+		NMSetting8021xCKScheme cert_scheme;
+		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+		if (cert_scheme == NM_SETTING_802_1X_CK_SCHEME_HASH) {
+			gtk_label_set_text (GTK_LABEL (widget),
+			                    _("<b>Note:</b> Server hash is used instead of CA certificate"));
+			gtk_label_set_use_markup (GTK_LABEL (widget), TRUE);
+		} else {
+			gtk_widget_hide (widget);
+		}
+	}
+
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_anon_identity_entry"));
 	if (s_8021x && nm_setting_802_1x_get_anonymous_identity (s_8021x))
 		gtk_entry_set_text (GTK_ENTRY (widget), nm_setting_802_1x_get_anonymous_identity (s_8021x));
@@ -376,10 +456,16 @@ eap_method_ttls_new (WirelessSecurity *ws_parent,
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_anon_identity_entry"));
 		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_subject_label"));
+		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_subject_entry"));
+		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_ca_cert_label"));
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_ca_cert_button"));
 		gtk_widget_hide (widget);
+		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_note_label"));
+		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_inner_auth_label"));
 		gtk_widget_hide (widget);
 		widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_inner_auth_combo"));
diff --git a/src/wireless-security/eap-method-ttls.ui b/src/wireless-security/eap-method-ttls.ui
index c3046c1..f39e9ab 100644
--- a/src/wireless-security/eap-method-ttls.ui
+++ b/src/wireless-security/eap-method-ttls.ui
@@ -19,7 +19,7 @@
         <child>
           <object class="GtkTable" id="table10">
             <property name="visible">True</property>
-            <property name="n_rows">4</property>
+            <property name="n_rows">6</property>
             <property name="n_columns">2</property>
             <property name="column_spacing">12</property>
             <property name="row_spacing">6</property>
@@ -49,6 +49,35 @@
               </packing>
             </child>
             <child>
+              <object class="GtkLabel" id="eap_ttls_subject_label">
+                <property name="visible">True</property>
+                <property name="xalign">0</property>
+                <property name="label" translatable="yes">_Subject:</property>
+                <property name="use_underline">True</property>
+                <property name="mnemonic_widget">eap_ttls_subject_entry</property>
+              </object>
+              <packing>
+                <property name="top_attach">1</property>
+                <property name="bottom_attach">2</property>
+                <property name="x_options">GTK_FILL</property>
+                <property name="y_options"></property>
+              </packing>
+            </child>
+            <child>
+              <object class="GtkEntry" id="eap_ttls_subject_entry">
+                <property name="visible">True</property>
+                <property name="can_focus">True</property>
+                <property name="activates_default">True</property>
+              </object>
+              <packing>
+                <property name="left_attach">1</property>
+                <property name="right_attach">2</property>
+                <property name="top_attach">1</property>
+                <property name="bottom_attach">2</property>
+                <property name="y_options"></property>
+              </packing>
+            </child>
+            <child>
               <object class="GtkLabel" id="eap_ttls_ca_cert_label">
                 <property name="visible">True</property>
                 <property name="xalign">0</property>
@@ -57,8 +86,8 @@
                 <property name="mnemonic_widget">eap_ttls_ca_cert_button</property>
               </object>
               <packing>
-                <property name="top_attach">1</property>
-                <property name="bottom_attach">2</property>
+                <property name="top_attach">2</property>
+                <property name="bottom_attach">3</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -70,13 +99,24 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">1</property>
-                <property name="bottom_attach">2</property>
+                <property name="top_attach">2</property>
+                <property name="bottom_attach">3</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
             </child>
             <child>
+              <object class="GtkLabel" id="eap_ttls_note_label">
+                <property name="visible">True</property>
+                <property name="label" translatable="yes">Note</property>
+              </object>
+              <packing>
+                <property name="right_attach">2</property>
+                <property name="top_attach">3</property>
+                <property name="bottom_attach">4</property>
+              </packing>
+            </child>
+            <child>
               <object class="GtkLabel" id="eap_ttls_inner_auth_label">
                 <property name="visible">True</property>
                 <property name="xalign">0</property>
@@ -85,8 +125,8 @@
                 <property name="mnemonic_widget">eap_ttls_inner_auth_combo</property>
               </object>
               <packing>
-                <property name="top_attach">2</property>
-                <property name="bottom_attach">3</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options"/>
               </packing>
@@ -105,8 +145,8 @@
               <packing>
                 <property name="left_attach">1</property>
                 <property name="right_attach">2</property>
-                <property name="top_attach">2</property>
-                <property name="bottom_attach">3</property>
+                <property name="top_attach">4</property>
+                <property name="bottom_attach">5</property>
                 <property name="x_options">GTK_FILL</property>
                 <property name="y_options">GTK_FILL</property>
               </packing>
@@ -122,8 +162,8 @@
               </object>
               <packing>
                 <property name="right_attach">2</property>
-                <property name="top_attach">3</property>
-                <property name="bottom_attach">4</property>
+                <property name="top_attach">5</property>
+                <property name="bottom_attach">6</property>
                 <property name="x_options">GTK_FILL</property>
               </packing>
             </child>
diff --git a/src/wireless-security/wireless-security.c b/src/wireless-security/wireless-security.c
index fc77777..acb77b3 100644
--- a/src/wireless-security/wireless-security.c
+++ b/src/wireless-security/wireless-security.c
@@ -472,9 +472,11 @@ ws_802_1x_fill_connection (WirelessSecurity *sec,
 	NMSettingWireless *s_wireless;
 	NMSettingWirelessSecurity *s_wireless_sec;
 	NMSetting8021x *s_8021x;
+	NMSetting8021xCKScheme cert_scheme;
 	EAPMethod *eap = NULL;
 	GtkTreeModel *model;
 	GtkTreeIter iter;
+	char *subject, *cert_hash;
 
 	s_wireless = nm_connection_get_setting_wireless (connection);
 	g_assert (s_wireless);
@@ -497,6 +499,26 @@ ws_802_1x_fill_connection (WirelessSecurity *sec,
 
 	eap_method_fill_connection (eap, connection);
 	eap_method_unref (eap);
+
+	/* Fetch subject and cert_hash from connection */
+	subject = (char *)g_object_get_data (G_OBJECT (connection), NMA_SERVER_SUBJECT);
+	if (subject && !nm_setting_802_1x_get_subject_match (s_8021x))
+		g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, subject, NULL);
+
+	cert_hash = (char *)g_object_get_data (G_OBJECT (connection), NMA_SERVER_CERT_HASH);
+	cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+	if (cert_hash && cert_scheme == NM_SETTING_802_1X_CK_SCHEME_UNKNOWN) {
+		NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN;
+		GError *error = NULL;
+		if (!nm_setting_802_1x_set_ca_cert (s_8021x,
+		                                    cert_hash,
+		                                    NM_SETTING_802_1X_CK_SCHEME_HASH,
+		                                    &format,
+		                                    &error)) {
+			g_warning ("Couldn't set CA certificate '%s': %s", cert_hash, error ? error->message : "(unknown)");
+			g_error_free (error);
+		}
+	}
 }
 
 void
diff --git a/src/wireless-security/wireless-security.h b/src/wireless-security/wireless-security.h
index eea98c3..3dda2ea 100644
--- a/src/wireless-security/wireless-security.h
+++ b/src/wireless-security/wireless-security.h
@@ -28,6 +28,9 @@
 
 #include <nm-connection.h>
 
+#define NMA_SERVER_SUBJECT "nma-server-subject"
+#define NMA_SERVER_CERT_HASH "mna-server-cert-hash"
+
 typedef struct _WirelessSecurity WirelessSecurity;
 
 typedef void (*WSChangedFunc) (WirelessSecurity *sec, gpointer user_data);
-- 
1.8.1.4


From 066392e2b34a0030d5b8f698708882cab4be28ab Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <chingpang@gmail.com>
Date: Fri, 8 Feb 2013 13:57:50 +0800
Subject: [PATCH 2/5] wifi: check the subject and the CA cerificate

---
 src/libnm-gtk/nm-wifi-dialog.c     | 239 +++++++++++++++++++++++++++++++++++++
 src/libnm-gtk/nm-wifi-dialog.h     |   4 +
 src/libnm-gtk/nm-wireless-dialog.c |  12 ++
 src/libnm-gtk/nm-wireless-dialog.h |   6 +
 4 files changed, 261 insertions(+)

diff --git a/src/libnm-gtk/nm-wifi-dialog.c b/src/libnm-gtk/nm-wifi-dialog.c
index 3532caa..0d48e1a 100644
--- a/src/libnm-gtk/nm-wifi-dialog.c
+++ b/src/libnm-gtk/nm-wifi-dialog.c
@@ -77,6 +77,10 @@ typedef struct {
 	GetSecretsInfo *secrets_info;
 
 	gboolean disposed;
+
+	/* For Server certificate probe */
+	guint cert_id;
+	guint timeout_id;
 } NMAWifiDialogPrivate;
 
 #define D_NAME_COLUMN		0
@@ -109,6 +113,236 @@ nma_wifi_dialog_get_nag_ignored (NMAWifiDialog *self)
 	return NMA_WIFI_DIALOG_GET_PRIVATE (self)->nag_ignored;
 }
 
+gboolean
+nma_wifi_dialog_need_cert_probe (NMAWifiDialog *self)
+{
+	NMAWifiDialogPrivate *priv;
+	NMSetting8021x *s_8021x;
+	NMSetting8021xCKScheme cert_scheme;
+	int i, num_eap;
+	char *subject, *cert_hash;
+	gboolean need_ca = FALSE;
+
+	g_return_val_if_fail (self != NULL, FALSE);
+
+	priv = NMA_WIFI_DIALOG_GET_PRIVATE (self);
+
+	s_8021x = nm_connection_get_setting_802_1x (priv->connection);
+	if (!s_8021x)
+		return FALSE;
+
+	num_eap = nm_setting_802_1x_get_num_eap_methods (s_8021x);
+	for (i = 0; i < num_eap; i++) {
+		const char *eap;
+		eap = nm_setting_802_1x_get_eap_method (s_8021x, i);
+		if (   g_strcmp0 (eap, "ttls") == 0
+		    || g_strcmp0 (eap, "peap") == 0
+		    || g_strcmp0 (eap, "tls") == 0) {
+			need_ca = TRUE;
+			break;
+		}
+	}
+
+	if (!need_ca)
+		return FALSE;
+
+	subject = (char *)g_object_get_data (G_OBJECT (priv->connection), NMA_SERVER_SUBJECT);
+	cert_hash = (char *)g_object_get_data (G_OBJECT (priv->connection), NMA_SERVER_CERT_HASH);
+	cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+
+	if (   (!subject && !nm_setting_802_1x_get_subject_match (s_8021x))
+	    || (!cert_hash && (cert_scheme == NM_SETTING_802_1X_CK_SCHEME_UNKNOWN)))
+		return TRUE;
+
+	return FALSE;
+}
+
+static gboolean
+show_probe_result_dialog (GtkWindow *parent,
+                          NMConnection *connection,
+                          NMSetting8021x *s_8021x,
+                          const char *subject,
+                          const char *cert_hash)
+{
+	NMSettingWireless *s_wireless;
+	GtkWidget *notify_dialog, *content;
+	GtkWidget *grid;
+	GtkWidget *context, *label, *entry;
+	char *ssid, *string;
+	int response_id;
+
+	s_wireless = nm_connection_get_setting_wireless (connection);
+	ssid = nm_utils_ssid_to_utf8 (nm_setting_wireless_get_ssid (s_wireless));
+
+	notify_dialog = gtk_dialog_new_with_buttons (ssid, parent,
+	                                             GTK_DIALOG_MODAL,
+	                                             GTK_STOCK_NO, GTK_RESPONSE_NO,
+	                                             GTK_STOCK_YES, GTK_RESPONSE_YES,
+	                                             NULL);
+	gtk_window_set_resizable (GTK_WINDOW (notify_dialog), FALSE);
+	content = gtk_dialog_get_content_area (GTK_DIALOG (notify_dialog));
+
+	grid = gtk_grid_new ();
+	gtk_grid_set_row_spacing (GTK_GRID (grid), 12);
+	gtk_container_set_border_width (GTK_CONTAINER (grid), 5);
+	gtk_container_add (GTK_CONTAINER (content), grid);
+
+	entry = gtk_entry_new ();
+	gtk_editable_set_editable (GTK_EDITABLE (entry), FALSE);
+	if (!cert_hash) {
+		string = g_strdup_printf ("<span weight=\"bold\" size=\"larger\">%s %s</span>\n\n%s\n%s",
+		                          _("Server Certificate Probed:"),
+		                          ssid,
+		                          _("The subject is going to be filled with the probe result."),
+		                          _("Do you agree?"));
+		label = gtk_label_new (_("Subject:"));
+		gtk_entry_set_text (GTK_ENTRY (entry), subject);
+	} else {
+		string = g_strdup_printf ("<span weight=\"bold\" size=\"larger\">%s %s</span>\n\n%s\n%s",
+		                          _("Server Certificate Probed:"),
+		                          ssid,
+		                          _("The CA certificate is going to be filled with the probed server hash."),
+		                          _("Do you agree?"));
+		label = gtk_label_new (_("CA Certificate:"));
+		gtk_entry_set_text (GTK_ENTRY (entry), cert_hash);
+	}
+	context = gtk_label_new (string);
+	g_free (string);
+	g_free (ssid);
+	gtk_label_set_line_wrap (GTK_LABEL (context), TRUE);
+	gtk_label_set_use_markup (GTK_LABEL (context), TRUE);
+	gtk_grid_attach (GTK_GRID (grid), context, 0, 0, 10, 1);
+	gtk_grid_attach (GTK_GRID (grid), label, 0, 1, 1, 1);
+	gtk_grid_attach (GTK_GRID (grid), entry, 1, 1, 9, 1);
+
+	gtk_widget_show_all (notify_dialog);
+
+	response_id = gtk_dialog_run (GTK_DIALOG (notify_dialog));
+
+	gtk_widget_destroy (notify_dialog);
+
+	if (response_id == GTK_RESPONSE_YES)
+		return TRUE;
+
+	return FALSE;
+}
+
+static void
+wifi_got_cert_cb (NMDeviceWifi *wifi,
+                  GHashTable *cert,
+                  gpointer user_data)
+{
+	NMAWifiDialog *self = NMA_WIFI_DIALOG (user_data);
+	NMAWifiDialogPrivate *priv;
+	NMSetting8021x *s_8021x;
+	const char *subject = NULL, *hash = NULL;
+	GValue *value;
+	gboolean response = FALSE;
+
+	priv = NMA_WIFI_DIALOG_GET_PRIVATE (self);
+
+	g_signal_handler_disconnect (NM_DEVICE_WIFI (priv->device), priv->cert_id);
+	if (priv->timeout_id) {
+		g_source_remove (priv->timeout_id);
+		priv->timeout_id = 0;
+	}
+
+	value = g_hash_table_lookup (cert, "subject");
+	if (value && G_VALUE_HOLDS_STRING (value))
+		subject = g_value_get_string (value);
+
+	value = g_hash_table_lookup (cert, "cert_hash");
+	if (value && G_VALUE_HOLDS_STRING (value))
+		hash = g_value_get_string (value);
+
+	if (!subject || !hash)
+		goto out;
+
+	s_8021x = nm_connection_get_setting_802_1x (priv->connection);
+	if (s_8021x) {
+		NMSetting8021xCKScheme cert_scheme;
+		char *hash_path = NULL;
+		gboolean ret;
+
+		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+		if (cert_scheme == NM_SETTING_802_1X_CK_SCHEME_UNKNOWN)
+			hash_path = g_strconcat ("hash://server/sha256/", hash, NULL);
+		ret = show_probe_result_dialog (gtk_window_get_transient_for (GTK_WINDOW (self)),
+		                                priv->connection,
+		                                s_8021x,
+		                                subject,
+		                                hash_path);
+		if (!ret) {
+			g_free (hash_path);
+			goto out;
+		}
+
+		g_object_set_data_full (G_OBJECT (priv->connection),
+		                        NMA_SERVER_SUBJECT, g_strdup (subject),
+		                        (GDestroyNotify) g_free);
+		g_object_set_data_full (G_OBJECT (priv->connection),
+		                        NMA_SERVER_CERT_HASH, hash_path,
+		                        (GDestroyNotify) g_free);
+		response = TRUE;
+	}
+out:
+	if (response)
+		gtk_dialog_response (GTK_DIALOG (self), GTK_RESPONSE_OK);
+	else
+		gtk_widget_show (GTK_WIDGET (self));
+}
+
+static gboolean
+wifi_cert_timeout_cb (gpointer user_data)
+{
+	NMAWifiDialog *self = (NMAWifiDialog *)user_data;
+	NMAWifiDialogPrivate *priv;
+
+	priv = NMA_WIFI_DIALOG_GET_PRIVATE (self);
+
+	priv->timeout_id = 0;
+
+	g_signal_handler_disconnect (NM_DEVICE_WIFI (priv->device), priv->cert_id);
+
+	gtk_widget_show (GTK_WIDGET (self));
+
+	return FALSE;
+}
+
+gboolean
+nma_wifi_dialog_probe_cert (NMAWifiDialog *self)
+{
+	NMAWifiDialogPrivate *priv;
+	NMSettingWireless *s_wireless;
+	NMDeviceWifi *wifi;
+	guint id;
+
+	g_return_val_if_fail (self != NULL, FALSE);
+
+	priv = NMA_WIFI_DIALOG_GET_PRIVATE (self);
+	wifi = NM_DEVICE_WIFI (priv->device);
+
+	s_wireless = nm_connection_get_setting_wireless (priv->connection);
+	if (!nm_device_wifi_probe_cert (wifi, nm_setting_wireless_get_ssid (s_wireless)))
+		return FALSE;
+
+	id = g_timeout_add_seconds (30,
+	                            (GSourceFunc)wifi_cert_timeout_cb,
+	                            (gpointer)self);
+	if (id <= 0) {
+		g_warning ("Failed to add timeout for server certificate probe");
+		return FALSE;
+	}
+	priv->timeout_id = id;
+
+	id = g_signal_connect (wifi, "cert-received", G_CALLBACK (wifi_got_cert_cb), self);
+	priv->cert_id = id;
+
+	gtk_widget_hide (GTK_WIDGET (self));
+
+	return TRUE;
+}
+
 static void
 size_group_clear (GtkSizeGroup *group)
 {
@@ -1180,6 +1414,9 @@ internal_init (NMAWifiDialog *self,
 	 */
 	priv->revalidate_id = g_idle_add (revalidate, self);
 
+	priv->cert_id = 0;
+	priv->timeout_id = 0;
+
 	return TRUE;
 }
 
@@ -1237,6 +1474,8 @@ nma_wifi_dialog_get_connection (NMAWifiDialog *self,
 		}
 
 		nm_connection_add_setting (connection, (NMSetting *) s_wireless);
+
+		priv->connection = g_object_ref (connection);
 	} else
 		connection = g_object_ref (priv->connection);
 
diff --git a/src/libnm-gtk/nm-wifi-dialog.h b/src/libnm-gtk/nm-wifi-dialog.h
index 35554cb..09184e7 100644
--- a/src/libnm-gtk/nm-wifi-dialog.h
+++ b/src/libnm-gtk/nm-wifi-dialog.h
@@ -77,5 +77,9 @@ void nma_wifi_dialog_set_nag_ignored (NMAWifiDialog *self, gboolean ignored);
 
 gboolean nma_wifi_dialog_get_nag_ignored (NMAWifiDialog *self);
 
+gboolean nma_wifi_dialog_need_cert_probe (NMAWifiDialog *dialog);
+
+gboolean nma_wifi_dialog_probe_cert (NMAWifiDialog *dialog);
+
 #endif	/* NMA_WIFI_DIALOG_H */
 
diff --git a/src/libnm-gtk/nm-wireless-dialog.c b/src/libnm-gtk/nm-wireless-dialog.c
index 38882af..718f8dc 100644
--- a/src/libnm-gtk/nm-wireless-dialog.c
+++ b/src/libnm-gtk/nm-wireless-dialog.c
@@ -81,3 +81,15 @@ nma_wireless_dialog_nag_user (NMAWirelessDialog *self)
 {
 	return nma_wifi_dialog_nag_user ((NMAWifiDialog *)self);
 }
+
+gboolean
+nma_wireless_dialog_need_cert_probe (NMAWirelessDialog *self)
+{
+	return nma_wifi_dialog_need_cert_probe ((NMAWifiDialog *)self);
+}
+
+gboolean
+nma_wireless_dialog_probe_cert (NMAWirelessDialog *self)
+{
+	return nma_wifi_dialog_probe_cert ((NMAWifiDialog *)self);
+}
diff --git a/src/libnm-gtk/nm-wireless-dialog.h b/src/libnm-gtk/nm-wireless-dialog.h
index c5e282b..190afcf 100644
--- a/src/libnm-gtk/nm-wireless-dialog.h
+++ b/src/libnm-gtk/nm-wireless-dialog.h
@@ -89,5 +89,11 @@ void nma_wireless_dialog_set_nag_ignored (NMAWirelessDialog *dialog, gboolean ig
 GLIB_DEPRECATED_FOR(nma_wifi_dialog_get_nag_ignored)
 gboolean nma_wireless_dialog_get_nag_ignored (NMAWirelessDialog *dialog);
 
+GLIB_DEPRECATED_FOR(nma_wifi_dialog_need_cert_probe)
+gboolean nma_wireless_dialog_need_cert_probe (NMAWirelessDialog *dialog);
+
+GLIB_DEPRECATED_FOR(nma_wifi_dialog_probe_cert)
+gboolean nma_wireless_dialog_probe_cert (NMAWirelessDialog *dialog);
+
 #endif	/* NMA_WIRELESS_DIALOG_H */
 
-- 
1.8.1.4


From bf7e8bd9218ae1547d0a4d9a71bf960d8743d152 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <chingpang@gmail.com>
Date: Fri, 8 Feb 2013 12:04:58 +0800
Subject: [PATCH 3/5] Keep the CA hash until it's replaced by a file

---
 src/wireless-security/eap-method-peap.c   | 10 +++++++---
 src/wireless-security/eap-method-tls.c    | 10 +++++++---
 src/wireless-security/eap-method-ttls.c   | 10 +++++++---
 src/wireless-security/wireless-security.c | 24 +++++++++++++++++++++++-
 4 files changed, 44 insertions(+), 10 deletions(-)

diff --git a/src/wireless-security/eap-method-peap.c b/src/wireless-security/eap-method-peap.c
index 5f58804..a71c96b 100644
--- a/src/wireless-security/eap-method-peap.c
+++ b/src/wireless-security/eap-method-peap.c
@@ -127,6 +127,7 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 {
 	NMSetting8021x *s_8021x;
 	NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN;
+	NMSetting8021xCKScheme cert_scheme;
 	GtkWidget *widget;
 	const char *text;
 	char *filename;
@@ -156,9 +157,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_ca_cert_button"));
 	g_assert (widget);
 	filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (widget));
-	if (!nm_setting_802_1x_set_ca_cert (s_8021x, filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
-		g_warning ("Couldn't read CA certificate '%s': %s", filename, error ? error->message : "(unknown)");
-		g_clear_error (&error);
+	cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+	if (filename || cert_scheme != NM_SETTING_802_1X_CK_SCHEME_HASH) {
+		if (!nm_setting_802_1x_set_ca_cert (s_8021x, filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
+			g_warning ("Couldn't read CA certificate '%s': %s", filename, error ? error->message : "(unknown)");
+			g_clear_error (&error);
+		}
 	}
 
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_version_combo"));
diff --git a/src/wireless-security/eap-method-tls.c b/src/wireless-security/eap-method-tls.c
index 22e53d0..507302d 100644
--- a/src/wireless-security/eap-method-tls.c
+++ b/src/wireless-security/eap-method-tls.c
@@ -127,6 +127,7 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 {
 	EAPMethodTLS *method = (EAPMethodTLS *) parent;
 	NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN;
+	NMSetting8021xCKScheme cert_scheme;
 	NMSetting8021x *s_8021x;
 	GtkWidget *widget;
 	char *ca_filename, *pk_filename, *cc_filename;
@@ -218,9 +219,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 			g_clear_error (&error);
 		}
 	} else {
-		if (!nm_setting_802_1x_set_ca_cert (s_8021x, ca_filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
-			g_warning ("Couldn't read CA certificate '%s': %s", ca_filename, error ? error->message : "(unknown)");
-			g_clear_error (&error);
+		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+		if (ca_filename || cert_scheme != NM_SETTING_802_1X_CK_SCHEME_HASH) {
+			if (!nm_setting_802_1x_set_ca_cert (s_8021x, ca_filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
+				g_warning ("Couldn't read CA certificate '%s': %s", ca_filename, error ? error->message : "(unknown)");
+				g_clear_error (&error);
+			}
 		}
 	}
 
diff --git a/src/wireless-security/eap-method-ttls.c b/src/wireless-security/eap-method-ttls.c
index 1fe8431..c8a953f 100644
--- a/src/wireless-security/eap-method-ttls.c
+++ b/src/wireless-security/eap-method-ttls.c
@@ -123,6 +123,7 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 {
 	NMSetting8021x *s_8021x;
 	NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN;
+	NMSetting8021xCKScheme cert_scheme;
 	GtkWidget *widget;
 	const char *text;
 	char *filename;
@@ -151,9 +152,12 @@ fill_connection (EAPMethod *parent, NMConnection *connection)
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_ca_cert_button"));
 	g_assert (widget);
 	filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (widget));
-	if (!nm_setting_802_1x_set_ca_cert (s_8021x, filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
-		g_warning ("Couldn't read CA certificate '%s': %s", filename, error ? error->message : "(unknown)");
-		g_clear_error (&error);
+	cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
+	if (filename || cert_scheme != NM_SETTING_802_1X_CK_SCHEME_HASH) {
+		if (!nm_setting_802_1x_set_ca_cert (s_8021x, filename, NM_SETTING_802_1X_CK_SCHEME_PATH, &format, &error)) {
+			g_warning ("Couldn't read CA certificate '%s': %s", filename, error ? error->message : "(unknown)");
+			g_clear_error (&error);
+		}
 	}
 
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_inner_auth_combo"));
diff --git a/src/wireless-security/wireless-security.c b/src/wireless-security/wireless-security.c
index acb77b3..b1d8cf2 100644
--- a/src/wireless-security/wireless-security.c
+++ b/src/wireless-security/wireless-security.c
@@ -471,16 +471,23 @@ ws_802_1x_fill_connection (WirelessSecurity *sec,
 	GtkWidget *widget;
 	NMSettingWireless *s_wireless;
 	NMSettingWirelessSecurity *s_wireless_sec;
-	NMSetting8021x *s_8021x;
+	NMSetting8021x *s_8021x, *old_s_8021x;
 	NMSetting8021xCKScheme cert_scheme;
 	EAPMethod *eap = NULL;
 	GtkTreeModel *model;
 	GtkTreeIter iter;
 	char *subject, *cert_hash;
+	char *old_hash = NULL;
 
 	s_wireless = nm_connection_get_setting_wireless (connection);
 	g_assert (s_wireless);
 
+	old_s_8021x = nm_connection_get_setting_802_1x (connection);
+	if (old_s_8021x &&
+	    nm_setting_802_1x_get_ca_cert_scheme (old_s_8021x) == NM_SETTING_802_1X_CK_SCHEME_HASH) {
+		old_hash = g_strdup (nm_setting_802_1x_get_ca_cert_hash (old_s_8021x));
+	}
+
 	g_object_set (s_wireless, NM_SETTING_WIRELESS_SEC, NM_SETTING_WIRELESS_SECURITY_SETTING_NAME, NULL);
 
 	/* Blow away the old wireless security setting by adding a clear one */
@@ -491,6 +498,21 @@ ws_802_1x_fill_connection (WirelessSecurity *sec,
 	s_8021x = (NMSetting8021x *) nm_setting_802_1x_new ();
 	nm_connection_add_setting (connection, (NMSetting *) s_8021x);
 
+	if (old_hash) {
+		NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN;
+		GError *error = NULL;
+		if (!nm_setting_802_1x_set_ca_cert (s_8021x,
+		                                    old_hash,
+		                                    NM_SETTING_802_1X_CK_SCHEME_HASH,
+		                                    &format,
+		                                    &error)) {
+			g_warning ("Couldn't set CA certificate '%s': %s", old_hash,
+			           error ? error->message : "(unknown)");
+			g_error_free (error);
+		}
+		g_free (old_hash);
+	}
+
 	widget = GTK_WIDGET (gtk_builder_get_object (sec->builder, combo_name));
 	model = gtk_combo_box_get_model (GTK_COMBO_BOX (widget));
 	gtk_combo_box_get_active_iter (GTK_COMBO_BOX (widget), &iter);
-- 
1.8.1.4


From 97e00d0256e8538025b4279e4ccadd4a7f5b0adb Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <chingpang@gmail.com>
Date: Thu, 25 Apr 2013 11:24:00 +0800
Subject: [PATCH 4/5] wifi: Use the updated probe method

---
 src/libnm-gtk/nm-wifi-dialog.c | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/src/libnm-gtk/nm-wifi-dialog.c b/src/libnm-gtk/nm-wifi-dialog.c
index 0d48e1a..eef5f31 100644
--- a/src/libnm-gtk/nm-wifi-dialog.c
+++ b/src/libnm-gtk/nm-wifi-dialog.c
@@ -313,7 +313,6 @@ gboolean
 nma_wifi_dialog_probe_cert (NMAWifiDialog *self)
 {
 	NMAWifiDialogPrivate *priv;
-	NMSettingWireless *s_wireless;
 	NMDeviceWifi *wifi;
 	guint id;
 
@@ -322,8 +321,7 @@ nma_wifi_dialog_probe_cert (NMAWifiDialog *self)
 	priv = NMA_WIFI_DIALOG_GET_PRIVATE (self);
 	wifi = NM_DEVICE_WIFI (priv->device);
 
-	s_wireless = nm_connection_get_setting_wireless (priv->connection);
-	if (!nm_device_wifi_probe_cert (wifi, nm_setting_wireless_get_ssid (s_wireless)))
+	if (!nm_device_wifi_probe_cert (wifi, priv->connection))
 		return FALSE;
 
 	id = g_timeout_add_seconds (30,
-- 
1.8.1.4


From 193b971ea7d75e63583518de06c5b1639cb43ce6 Mon Sep 17 00:00:00 2001
From: Gary Ching-Pang Lin <chingpang@gmail.com>
Date: Thu, 25 Apr 2013 11:36:21 +0800
Subject: [PATCH 5/5] wifi: show the note widget only if necessary

---
 src/wireless-security/eap-method-peap.c | 4 ++--
 src/wireless-security/eap-method-ttls.c | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/src/wireless-security/eap-method-peap.c b/src/wireless-security/eap-method-peap.c
index a71c96b..81ba970 100644
--- a/src/wireless-security/eap-method-peap.c
+++ b/src/wireless-security/eap-method-peap.c
@@ -455,6 +455,7 @@ eap_method_peap_new (WirelessSecurity *ws_parent,
 	                  ws_parent);
 
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_peap_note_label"));
+	gtk_widget_hide (widget);
 	if (s_8021x) {
 		NMSetting8021xCKScheme cert_scheme;
 		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
@@ -462,8 +463,7 @@ eap_method_peap_new (WirelessSecurity *ws_parent,
 			gtk_label_set_text (GTK_LABEL (widget),
 			                    _("<b>Note:</b> Server hash is used instead of CA certificate"));
 			gtk_label_set_use_markup (GTK_LABEL (widget), TRUE);
-		} else {
-			gtk_widget_hide (widget);
+			gtk_widget_show (widget);
 		}
 	}
 
diff --git a/src/wireless-security/eap-method-ttls.c b/src/wireless-security/eap-method-ttls.c
index c8a953f..f195414 100644
--- a/src/wireless-security/eap-method-ttls.c
+++ b/src/wireless-security/eap-method-ttls.c
@@ -433,6 +433,7 @@ eap_method_ttls_new (WirelessSecurity *ws_parent,
 	                  ws_parent);
 
 	widget = GTK_WIDGET (gtk_builder_get_object (parent->builder, "eap_ttls_note_label"));
+	gtk_widget_hide (widget);
 	if (s_8021x) {
 		NMSetting8021xCKScheme cert_scheme;
 		cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x);
@@ -440,8 +441,7 @@ eap_method_ttls_new (WirelessSecurity *ws_parent,
 			gtk_label_set_text (GTK_LABEL (widget),
 			                    _("<b>Note:</b> Server hash is used instead of CA certificate"));
 			gtk_label_set_use_markup (GTK_LABEL (widget), TRUE);
-		} else {
-			gtk_widget_hide (widget);
+			gtk_widget_show (widget);
 		}
 	}
 
-- 
1.8.1.4

openSUSE Build Service is sponsored by