Sign Up
Log In
Log In
or
Sign Up
Places
All Projects
Status Monitor
Collapse sidebar
openSUSE:Evergreen:11.4
NetworkManager-gnome.import5627
nma-wpa-eap-probe-ca-cert.patch
Overview
Repositories
Revisions
Requests
Users
Attributes
Meta
File nma-wpa-eap-probe-ca-cert.patch of Package NetworkManager-gnome.import5627
diff --git a/src/applet-device-wifi.c b/src/applet-device-wifi.c index 39c2f91..576a765 100644 --- a/src/applet-device-wifi.c +++ b/src/applet-device-wifi.c @@ -1428,6 +1428,11 @@ wireless_dialog_response_cb (GtkDialog *foo, g_assert (connection); g_assert (device); + if (nma_wireless_dialog_need_ca_cert_probe (dialog)) { + nma_wireless_dialog_probe_ca_cert (dialog); + return; + } + /* If it's a system connection we just need to tell NM to activate it */ if (nm_connection_get_scope (connection) == NM_CONNECTION_SCOPE_SYSTEM) { service = NM_DBUS_SERVICE_SYSTEM_SETTINGS; @@ -1661,6 +1666,11 @@ get_secrets_dialog_response_cb (GtkDialog *foo, goto done; } + if (nma_wireless_dialog_need_ca_cert_probe (dialog)) { + nma_wireless_dialog_probe_ca_cert (dialog); + return; + } + /* Second-guess which setting NM wants secrets for. */ s_wireless_sec = NM_SETTING_WIRELESS_SECURITY (nm_connection_get_setting (connection, NM_TYPE_SETTING_WIRELESS_SECURITY)); if (!s_wireless_sec) { diff --git a/src/applet.glade b/src/applet.glade index 5d1763d..c194cfa 100644 --- a/src/applet.glade +++ b/src/applet.glade @@ -1135,7 +1135,7 @@ Shared Key</property> <child> <widget 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> @@ -1172,8 +1172,8 @@ Shared Key</property> <property name="mnemonic_widget">eap_ttls_ca_cert_button</property> </widget> <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"></property> </packing> @@ -1185,8 +1185,8 @@ Shared Key</property> <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> @@ -1200,8 +1200,8 @@ Shared Key</property> <property name="mnemonic_widget">eap_ttls_inner_auth_combo</property> </widget> <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"></property> </packing> @@ -1214,8 +1214,8 @@ Shared Key</property> <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> @@ -1231,9 +1231,67 @@ Shared Key</property> </widget> <packing> <property name="right_attach">2</property> + <property name="top_attach">5</property> + <property name="bottom_attach">6</property> + <property name="x_options">GTK_FILL</property> + </packing> + </child> + <child> + <widget class="GtkLabel" id="eap_ttls_subject_label"> + <property name="visible">True</property> + <property name="label" translatable="yes">Subject:</property> + <property name="use_underline">False</property> + <property name="use_markup">False</property> + <property name="justify">GTK_JUSTIFY_LEFT</property> + <property name="wrap">False</property> + <property name="selectable">False</property> + <property name="xalign">0</property> + <property name="yalign">0.5</property> + <property name="xpad">0</property> + <property name="ypad">0</property> + <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> + <property name="width_chars">-1</property> + <property name="single_line_mode">False</property> + <property name="angle">0</property> + </widget> + <packing> + <property name="left_attach">0</property> + <property name="right_attach">1</property> + <property name="top_attach">1</property> + <property name="bottom_attach">2</property> + <property name="x_options">fill</property> + <property name="y_options"></property> + </packing> + </child> + <child> + <widget class="GtkEntry" id="eap_ttls_subject_entry"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="editable">True</property> + <property name="visibility">True</property> + <property name="max_length">0</property> + <property name="text" translatable="yes"></property> + <property name="has_frame">True</property> + <property name="activates_default">False</property> + </widget> + <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> + <widget class="GtkLabel" id="eap_ttls_note_label"> + <property name="visible">True</property> + <property name="label" translatable="yes">Note</property> + <property name="track_visited_links">False</property> + </widget> + <packing> + <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> </packing> </child> </widget> @@ -1652,7 +1710,7 @@ Shared Key</property> <child> <widget 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> @@ -1689,8 +1747,8 @@ Shared Key</property> <property name="mnemonic_widget">eap_peap_ca_cert_button</property> </widget> <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"></property> </packing> @@ -1702,8 +1760,8 @@ Shared Key</property> <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> @@ -1718,8 +1776,8 @@ Shared Key</property> </widget> <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> @@ -1732,8 +1790,8 @@ Shared Key</property> <property name="mnemonic_widget">eap_peap_inner_auth_combo</property> </widget> <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"></property> </packing> @@ -1746,8 +1804,8 @@ Shared Key</property> <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> @@ -1761,8 +1819,8 @@ Shared Key</property> <property name="mnemonic_widget">eap_peap_version_combo</property> </widget> <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"></property> </packing> @@ -1777,12 +1835,70 @@ Version 1</property> <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> </child> + <child> + <widget class="GtkLabel" id="eap_peap_subject_label"> + <property name="visible">True</property> + <property name="label" translatable="yes">Subject:</property> + <property name="use_underline">False</property> + <property name="use_markup">False</property> + <property name="justify">GTK_JUSTIFY_LEFT</property> + <property name="wrap">False</property> + <property name="selectable">False</property> + <property name="xalign">0</property> + <property name="yalign">0.5</property> + <property name="xpad">0</property> + <property name="ypad">0</property> + <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> + <property name="width_chars">-1</property> + <property name="single_line_mode">False</property> + <property name="angle">0</property> + </widget> + <packing> + <property name="left_attach">0</property> + <property name="right_attach">1</property> + <property name="top_attach">1</property> + <property name="bottom_attach">2</property> + <property name="x_options">fill</property> + <property name="y_options"></property> + </packing> + </child> + <child> + <widget class="GtkEntry" id="eap_peap_subject_entry"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="editable">True</property> + <property name="visibility">True</property> + <property name="max_length">0</property> + <property name="text" translatable="yes"></property> + <property name="has_frame">True</property> + <property name="activates_default">False</property> + </widget> + <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> + <widget class="GtkLabel" id="eap_peap_note_label"> + <property name="visible">True</property> + <property name="label" translatable="yes">Note</property> + <property name="track_visited_links">False</property> + </widget> + <packing> + <property name="right_attach">2</property> + <property name="top_attach">3</property> + <property name="bottom_attach">4</property> + </packing> + </child> </widget> </child> <child> diff --git a/src/gconf-helpers/gconf-helpers.c b/src/gconf-helpers/gconf-helpers.c index 2e0db07..0858736 100644 --- a/src/gconf-helpers/gconf-helpers.c +++ b/src/gconf-helpers/gconf-helpers.c @@ -1719,6 +1719,7 @@ typedef struct ReadFromGConfInfo { } ReadFromGConfInfo; #define FILE_TAG "file://" +#define HASH_TAG "hash://server/sha256/" static void read_one_setting_value_from_gconf (NMSetting *setting, @@ -1770,9 +1771,14 @@ read_one_setting_value_from_gconf (NMSetting *setting, if (nm_gconf_get_string_helper (info->client, info->dir, key, setting_name, &str_val)) { GByteArray *ba_val; - ba_val = g_byte_array_sized_new (strlen (FILE_TAG) + strlen (str_val) + 1); - g_byte_array_append (ba_val, (const guint8 *) FILE_TAG, strlen (FILE_TAG)); - g_byte_array_append (ba_val, (const guint8 *) str_val, strlen (str_val) + 1); /* +1 for the trailing NULL */ + if (g_str_has_prefix (str_val, HASH_TAG)) { + ba_val = g_byte_array_sized_new (strlen (str_val) + 1); + g_byte_array_append (ba_val, (const guint8 *) str_val, strlen (str_val) + 1); + } else { + ba_val = g_byte_array_sized_new (strlen (FILE_TAG) + strlen (str_val) + 1); + g_byte_array_append (ba_val, (const guint8 *) FILE_TAG, strlen (FILE_TAG)); + g_byte_array_append (ba_val, (const guint8 *) str_val, strlen (str_val) + 1); /* +1 for the trailing NULL */ + } g_object_set (setting, key, ba_val, NULL); g_byte_array_free (ba_val, TRUE); g_free (str_val); @@ -2188,6 +2194,7 @@ out: typedef NMSetting8021xCKScheme (*SchemeFunc) (NMSetting8021x *setting); typedef const char * (*PathFunc) (NMSetting8021x *setting); typedef const GByteArray * (*BlobFunc) (NMSetting8021x *setting); +typedef const char * (*HashFunc) (NMSetting8021x *setting); typedef NMSetting8021xCKFormat (*FormatFunc) (NMSetting8021x *setting); typedef const char * (*PasswordFunc)(NMSetting8021x *setting); @@ -2197,6 +2204,7 @@ typedef struct ObjectType { SchemeFunc scheme_func; PathFunc path_func; BlobFunc blob_func; + HashFunc hash_func; FormatFunc format_func; PasswordFunc password_func; const char *privkey_password_key; @@ -2209,6 +2217,7 @@ static const ObjectType ca_type = { nm_setting_802_1x_get_ca_cert_scheme, nm_setting_802_1x_get_ca_cert_path, nm_setting_802_1x_get_ca_cert_blob, + nm_setting_802_1x_get_ca_cert_hash, NULL, NULL, NULL, @@ -2224,6 +2233,7 @@ static const ObjectType phase2_ca_type = { NULL, NULL, NULL, + NULL, "inner-ca-cert.der" }; @@ -2236,6 +2246,7 @@ static const ObjectType client_type = { NULL, NULL, NULL, + NULL, "client-cert.der" }; @@ -2248,6 +2259,7 @@ static const ObjectType phase2_client_type = { NULL, NULL, NULL, + NULL, "inner-client-cert.der" }; @@ -2257,6 +2269,7 @@ static const ObjectType pk_type = { nm_setting_802_1x_get_private_key_scheme, nm_setting_802_1x_get_private_key_path, nm_setting_802_1x_get_private_key_blob, + NULL, nm_setting_802_1x_get_private_key_format, nm_setting_802_1x_get_private_key_password, NM_SETTING_802_1X_PRIVATE_KEY_PASSWORD, @@ -2269,6 +2282,7 @@ static const ObjectType phase2_pk_type = { nm_setting_802_1x_get_phase2_private_key_scheme, nm_setting_802_1x_get_phase2_private_key_path, nm_setting_802_1x_get_phase2_private_key_blob, + NULL, nm_setting_802_1x_get_phase2_private_key_format, nm_setting_802_1x_get_phase2_private_key_password, NM_SETTING_802_1X_PHASE2_PRIVATE_KEY_PASSWORD, @@ -2281,6 +2295,7 @@ static const ObjectType p12_type = { nm_setting_802_1x_get_private_key_scheme, nm_setting_802_1x_get_private_key_path, nm_setting_802_1x_get_private_key_blob, + NULL, nm_setting_802_1x_get_private_key_format, nm_setting_802_1x_get_private_key_password, NM_SETTING_802_1X_PRIVATE_KEY_PASSWORD, @@ -2293,6 +2308,7 @@ static const ObjectType phase2_p12_type = { nm_setting_802_1x_get_phase2_private_key_scheme, nm_setting_802_1x_get_phase2_private_key_path, nm_setting_802_1x_get_phase2_private_key_blob, + NULL, nm_setting_802_1x_get_phase2_private_key_format, nm_setting_802_1x_get_phase2_private_key_password, NM_SETTING_802_1X_PHASE2_PRIVATE_KEY_PASSWORD, @@ -2335,6 +2351,9 @@ write_object (GConfClient *client, case NM_SETTING_802_1X_CK_SCHEME_PATH: path = (*(objtype->path_func))(s_8021x); break; + case NM_SETTING_802_1X_CK_SCHEME_HASH: + path = (*(objtype->hash_func))(s_8021x); + break; default: break; } diff --git a/src/wireless-dialog.c b/src/wireless-dialog.c index 621526f..d6cc4c2 100644 --- a/src/wireless-dialog.c +++ b/src/wireless-dialog.c @@ -37,6 +37,7 @@ #include <nm-setting-connection.h> #include <nm-setting-wireless.h> #include <nm-setting-ip4-config.h> +#include <nm-setting-8021x.h> #include "applet.h" #include "applet-dialogs.h" @@ -83,6 +84,10 @@ typedef struct { GetSecretsInfo *secrets_info; gboolean disposed; + + /* For Server certificate probe */ + guint ca_cert_id; + guint timeout_id; } NMAWirelessDialogPrivate; #define D_NAME_COLUMN 0 @@ -115,6 +120,228 @@ nma_wireless_dialog_get_nag_ignored (NMAWirelessDialog *self) return NMA_WIRELESS_DIALOG_GET_PRIVATE (self)->nag_ignored; } +gboolean +nma_wireless_dialog_need_ca_cert_probe (NMAWirelessDialog *self) +{ + NMAWirelessDialogPrivate *priv; + NMSetting8021x *s_8021x; + NMSetting8021xCKScheme cert_scheme; + int i, num_eap; + const char *subject; + gboolean need_ca = FALSE; + + g_return_val_if_fail (self != NULL, FALSE); + + priv = NMA_WIRELESS_DIALOG_GET_PRIVATE (self); + + s_8021x = NM_SETTING_802_1X (nm_connection_get_setting (priv->connection, NM_TYPE_SETTING_802_1X)); + 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) { + need_ca = TRUE; + break; + } + } + + if (!need_ca) + return FALSE; + + subject = nm_setting_802_1x_get_subject_match (s_8021x); + cert_scheme = nm_setting_802_1x_get_ca_cert_scheme (s_8021x); + + if (!subject || 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) +{ + NMSettingConnection *s_con; + GtkWidget *notify_dialog, *content; + GtkWidget *table; + GtkWidget *context, *label, *entry; + char *id, *string; + int response_id; + + s_con = NM_SETTING_CONNECTION (nm_connection_get_setting (connection, NM_TYPE_SETTING_CONNECTION)); + id = (char *) nm_setting_connection_get_id (s_con); + + notify_dialog = gtk_dialog_new_with_buttons (id, parent, + GTK_DIALOG_MODAL, + GTK_STOCK_NO, GTK_RESPONSE_NO, + GTK_STOCK_YES, GTK_RESPONSE_YES, + NULL); + content = gtk_dialog_get_content_area (GTK_DIALOG (notify_dialog)); + + table = gtk_table_new (2, 3, FALSE); + gtk_table_set_row_spacings (GTK_TABLE (table), 10); + gtk_container_set_border_width (GTK_CONTAINER (table), 6); + gtk_container_add (GTK_CONTAINER (content), table); + + entry = gtk_entry_new (); + gtk_editable_set_editable (GTK_EDITABLE (entry), FALSE); + if (!cert_hash) { + string = g_strdup_printf (_("<span weight=\"bold\" size=\"larger\">Server Certificate Probed</span>\n\nThe subject of <b>%s</b> is going to be filled with the probe result. Do you agree?"), id); + label = gtk_label_new (_("Subject:")); + gtk_entry_set_text (GTK_ENTRY (entry), subject); + } else { + string = g_strdup_printf (_("<span weight=\"bold\" size=\"larger\">Server Certificate Probed</span>\n\nThe CA certificate of <b>%s</b> is going to be filled with the probed server hash. Do you agree?"), id); + label = gtk_label_new (_("CA Certificate:")); + gtk_entry_set_text (GTK_ENTRY (entry), cert_hash); + } + context = gtk_label_new (string); + g_free (string); + gtk_label_set_line_wrap (GTK_LABEL (context), TRUE); + gtk_label_set_use_markup (GTK_LABEL (context), TRUE); + gtk_table_attach (GTK_TABLE (table), context, 0, 3, 0, 1, GTK_FILL, GTK_FILL, 0, 0); + gtk_table_attach (GTK_TABLE (table), label, 0, 1, 1, 2, GTK_FILL, GTK_FILL, 0, 0); + gtk_table_attach (GTK_TABLE (table), entry, 1, 3, 1, 2, GTK_FILL, GTK_FILL, 0, 0); + + 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 +wireless_ca_cert_cb (NMDeviceWifi *wifi, + GHashTable *ca_cert, + gpointer user_data) +{ + NMAWirelessDialog *self = NMA_WIRELESS_DIALOG (user_data); + NMAWirelessDialogPrivate *priv; + NMSetting8021x *s_8021x; + const char *subject = NULL, *hash = NULL; + gboolean response = FALSE; + + priv = NMA_WIRELESS_DIALOG_GET_PRIVATE (self); + + g_signal_handler_disconnect (NM_DEVICE_WIFI (priv->device), priv->ca_cert_id); + if (priv->timeout_id) { + g_source_remove (priv->timeout_id); + priv->timeout_id = 0; + } + + subject = (const char *)g_hash_table_lookup (ca_cert, "subject"); + hash = (const char *)g_hash_table_lookup (ca_cert, "hash"); + + if (!subject || !hash) + goto out; + + s_8021x = NM_SETTING_802_1X (nm_connection_get_setting (priv->connection, NM_TYPE_SETTING_802_1X)); + if (s_8021x) { + NMSetting8021xCKScheme cert_scheme; + char *hash_path = NULL; + gboolean ret; + GError *error = NULL; + + 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 (self), + priv->connection, + s_8021x, + subject, + hash_path); + if (!ret) { + g_free (hash_path); + goto out; + } + + if (!nm_setting_802_1x_get_subject_match (s_8021x)) + g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, subject, NULL); + if (hash_path) { + NMSetting8021xCKFormat format = NM_SETTING_802_1X_CK_FORMAT_UNKNOWN; + nm_setting_802_1x_set_ca_cert (s_8021x, + hash_path, + NM_SETTING_802_1X_CK_SCHEME_HASH, + &format, + &error); + g_free (hash_path); + if (error) { + g_warning ("Failed to set certificate hash: (%d) %s", error->code, error->message); + g_error_free (error); + goto out; + } + } + response = TRUE; + } +out: + if (response) + gtk_dialog_response (GTK_DIALOG (self), GTK_RESPONSE_OK); + else + gtk_widget_show (GTK_WIDGET (self)); +} + +static gboolean +wireless_ca_cert_timeout_cb (gpointer user_data) +{ + NMAWirelessDialog *self = (NMAWirelessDialog *)user_data; + NMAWirelessDialogPrivate *priv; + + priv = NMA_WIRELESS_DIALOG_GET_PRIVATE (self); + + priv->timeout_id = 0; + + g_signal_handler_disconnect (NM_DEVICE_WIFI (priv->device), priv->ca_cert_id); + + gtk_widget_show (GTK_WIDGET (self)); + + return FALSE; +} + +gboolean +nma_wireless_dialog_probe_ca_cert (NMAWirelessDialog *self) +{ + NMAWirelessDialogPrivate *priv; + NMSettingWireless *s_wireless; + NMDeviceWifi *wifi; + guint id; + + g_return_val_if_fail (self != NULL, FALSE); + + priv = NMA_WIRELESS_DIALOG_GET_PRIVATE (self); + wifi = NM_DEVICE_WIFI (priv->device); + + s_wireless = (NMSettingWireless *) nm_connection_get_setting (priv->connection, NM_TYPE_SETTING_WIRELESS); + if (!nm_device_wifi_probe_ca_cert (wifi, nm_setting_wireless_get_ssid (s_wireless))) + return FALSE; + + id = g_timeout_add_seconds (30, + (GSourceFunc)wireless_ca_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, "ca-cert-received", G_CALLBACK (wireless_ca_cert_cb), self); + priv->ca_cert_id = id; + + gtk_widget_hide (GTK_WIDGET (self)); + + return TRUE; +} + static void model_free (GtkTreeModel *model, guint col) { diff --git a/src/wireless-dialog.h b/src/wireless-dialog.h index 3b9ee4d..16f6160 100644 --- a/src/wireless-dialog.h +++ b/src/wireless-dialog.h @@ -66,5 +66,9 @@ void nma_wireless_dialog_set_nag_ignored (NMAWirelessDialog *dialog, gboolean ig gboolean nma_wireless_dialog_get_nag_ignored (NMAWirelessDialog *dialog); +gboolean nma_wireless_dialog_need_ca_cert_probe (NMAWirelessDialog *dialog); + +gboolean nma_wireless_dialog_probe_ca_cert (NMAWirelessDialog *dialog); + #endif /* WIRELESS_DIALOG_H */ diff --git a/src/wireless-security/eap-method-peap.c b/src/wireless-security/eap-method-peap.c index 49faf12..fdab1cc 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>") + static void destroy (EAPMethod *parent) { @@ -98,6 +100,10 @@ add_to_size_group (EAPMethod *parent, GtkSizeGroup *group) g_assert (widget); gtk_size_group_add_widget (group, widget); + widget = glade_xml_get_widget (parent->xml, "eap_peap_subject_label"); + g_assert (widget); + gtk_size_group_add_widget (group, widget); + widget = glade_xml_get_widget (parent->xml, "eap_peap_inner_auth_combo"); g_assert (widget); @@ -138,10 +144,16 @@ fill_connection (EAPMethod *parent, NMConnection *connection) if (text && strlen (text)) g_object_set (s_8021x, NM_SETTING_802_1X_ANONYMOUS_IDENTITY, text, NULL); + widget = glade_xml_get_widget (parent->xml, "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 = glade_xml_get_widget (parent->xml, "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)) { + if (filename && !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); } @@ -305,6 +317,43 @@ 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_modify_text (GTK_WIDGET (widget), GTK_STATE_NORMAL, NULL); + } + return FALSE; +} + +static gboolean +subject_entry_focus_out_cb (GtkWidget *widget, + GdkEvent *event, + gpointer user_data) +{ + NMSetting8021x *s_8021x = (NMSetting8021x *)user_data; + const char *text = gtk_entry_get_text (GTK_ENTRY (widget)); + GtkStyle *style; + + if (!text || !strlen (text)) { + /* Since we save/restore the subject in ws_802_1x_fill_connection() + * to prevent the probed result from being erased, we have to clear + * the subject here to trigger the probe later. */ + g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, NULL, NULL); + gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE); + style = gtk_widget_get_style (widget); + gtk_widget_modify_text (GTK_WIDGET (widget), + GTK_STATE_NORMAL, + &style->text[GTK_STATE_INSENSITIVE]); + } + + return FALSE; +} + EAPMethodPEAP * eap_method_peap_new (const char *glade_file, WirelessSecurity *parent, @@ -406,6 +455,43 @@ eap_method_peap_new (const char *glade_file, (GCallback) wireless_security_changed_cb, parent); + widget = glade_xml_get_widget (xml, "eap_peap_subject_entry"); + if (s_8021x) { + const char *text = nm_setting_802_1x_get_subject_match (s_8021x); + if (!text) { + GtkStyle *style; + style = gtk_widget_get_style (widget); + gtk_widget_modify_text (widget, + GTK_STATE_NORMAL, + &style->text[GTK_STATE_INSENSITIVE]); + 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, + s_8021x); + } + g_signal_connect (G_OBJECT (widget), "changed", + (GCallback) wireless_security_changed_cb, + parent); + + widget = glade_xml_get_widget (xml, "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); + } + } + return method; } diff --git a/src/wireless-security/eap-method-ttls.c b/src/wireless-security/eap-method-ttls.c index 4d9b9bc..68f94d1 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>") + static void destroy (EAPMethod *parent) { @@ -86,6 +88,10 @@ add_to_size_group (EAPMethod *parent, GtkSizeGroup *group) g_assert (widget); gtk_size_group_add_widget (group, widget); + widget = glade_xml_get_widget (parent->xml, "eap_ttls_subject_label"); + g_assert (widget); + gtk_size_group_add_widget (group, widget); + widget = glade_xml_get_widget (parent->xml, "eap_ttls_ca_cert_label"); g_assert (widget); gtk_size_group_add_widget (group, widget); @@ -133,10 +139,16 @@ fill_connection (EAPMethod *parent, NMConnection *connection) if (text && strlen (text)) g_object_set (s_8021x, NM_SETTING_802_1X_ANONYMOUS_IDENTITY, text, NULL); + widget = glade_xml_get_widget (parent->xml, "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 = glade_xml_get_widget (parent->xml, "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)) { + if (filename && !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); } @@ -304,6 +316,43 @@ 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_modify_text (GTK_WIDGET (widget), GTK_STATE_NORMAL, NULL); + } + return FALSE; +} + +static gboolean +subject_entry_focus_out_cb (GtkWidget *widget, + GdkEvent *event, + gpointer user_data) +{ + NMSetting8021x *s_8021x = (NMSetting8021x *)user_data; + const char *text = gtk_entry_get_text (GTK_ENTRY (widget)); + GtkStyle *style; + + if (!text || !strlen (text)) { + /* Since we save/restore the subject in ws_802_1x_fill_connection() + * to prevent the probed result from being erased, we have to clear + * the subject here to trigger the probe later. */ + g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, NULL, NULL); + gtk_entry_set_text (GTK_ENTRY (widget), SUBJECT_NOTE); + style = gtk_widget_get_style (widget); + gtk_widget_modify_text (GTK_WIDGET (widget), + GTK_STATE_NORMAL, + &style->text[GTK_STATE_INSENSITIVE]); + } + + return FALSE; +} + EAPMethodTTLS * eap_method_ttls_new (const char *glade_file, WirelessSecurity *parent, @@ -383,6 +432,44 @@ eap_method_ttls_new (const char *glade_file, (GCallback) wireless_security_changed_cb, parent); + widget = glade_xml_get_widget (xml, "eap_ttls_subject_entry"); + if (s_8021x) { + const char *text = nm_setting_802_1x_get_subject_match (s_8021x); + if (!text) { + GtkStyle *style; + style = gtk_widget_get_style (widget); + gtk_widget_modify_text (widget, + GTK_STATE_NORMAL, + &style->text[GTK_STATE_INSENSITIVE]); + 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, + s_8021x); + + } + g_signal_connect (G_OBJECT (widget), "changed", + (GCallback) wireless_security_changed_cb, + parent); + + widget = glade_xml_get_widget (xml, "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 = inner_auth_combo_init (method, glade_file, connection, s_8021x); inner_auth_combo_changed_cb (widget, (gpointer) method); diff --git a/src/wireless-security/wireless-security.c b/src/wireless-security/wireless-security.c index 1a51e6b..96a2841 100644 --- a/src/wireless-security/wireless-security.c +++ b/src/wireless-security/wireless-security.c @@ -393,6 +393,7 @@ ws_802_1x_fill_connection (WirelessSecurity *sec, EAPMethod *eap = NULL; GtkTreeModel *model; GtkTreeIter iter; + char *subject = NULL, *cert_hash = NULL; s_wireless = NM_SETTING_WIRELESS (nm_connection_get_setting (connection, NM_TYPE_SETTING_WIRELESS)); g_assert (s_wireless); @@ -403,10 +404,36 @@ ws_802_1x_fill_connection (WirelessSecurity *sec, s_wireless_sec = (NMSettingWirelessSecurity *) nm_setting_wireless_security_new (); nm_connection_add_setting (connection, (NMSetting *) s_wireless_sec); + /* Fetch the server info */ + s_8021x = NM_SETTING_802_1X (nm_connection_get_setting (connection, NM_TYPE_SETTING_802_1X)); + if (s_8021x) { + subject = g_strdup (nm_setting_802_1x_get_subject_match (s_8021x)); + if (nm_setting_802_1x_get_ca_cert_scheme (s_8021x) == NM_SETTING_802_1X_CK_SCHEME_HASH) + cert_hash = g_strdup (nm_setting_802_1x_get_ca_cert_hash (s_8021x)); + } + /* Blow away the old 802.1x setting by adding a clear one */ s_8021x = (NMSetting8021x *) nm_setting_802_1x_new (); nm_connection_add_setting (connection, (NMSetting *) s_8021x); + /* Restore the server info */ + if (subject) { + g_object_set (s_8021x, NM_SETTING_802_1X_SUBJECT_MATCH, subject, NULL); + g_free (subject); + } + if (cert_hash) { + 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_error_free (error); + } + g_free (cert_hash); + } + widget = glade_xml_get_widget (sec->xml, combo_name); model = gtk_combo_box_get_model (GTK_COMBO_BOX (widget)); gtk_combo_box_get_active_iter (GTK_COMBO_BOX (widget), &iter);
Locations
Projects
Search
Status Monitor
Help
OpenBuildService.org
Documentation
API Documentation
Code of Conduct
Contact
Support
@OBShq
Terms
openSUSE Build Service is sponsored by
The Open Build Service is an
openSUSE project
.
Sign Up
Log In
Places
Places
All Projects
Status Monitor