summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthias Clasen <mclasen@redhat.com>2012-12-17 14:17:42 -0500
committerMatthias Clasen <mclasen@redhat.com>2012-12-21 21:57:31 -0500
commitaee2cc08f711453b835b33f72b7c610daf8bb2cd (patch)
tree77a985aba974365394cd39a161af3282ff71d916
parentea55585aa28abb3e1ef65d80585f81c953460098 (diff)
downloadgnome-control-center-wip/network.tar.gz
network: Implement the new design for wiredwip/network
This expands the connection editor to cover ethernet, and adds support for multiple wired profiles.
-rw-r--r--panels/network/Makefile.am1
-rw-r--r--panels/network/connection-editor/Makefile.am9
-rw-r--r--panels/network/connection-editor/ce-page-8021x-security.c188
-rw-r--r--panels/network/connection-editor/ce-page-8021x-security.h64
-rw-r--r--panels/network/connection-editor/ce-page-details.c45
-rw-r--r--panels/network/connection-editor/ce-page-ethernet.c304
-rw-r--r--panels/network/connection-editor/ce-page-ethernet.h75
-rw-r--r--panels/network/connection-editor/ce-page-ip4.c4
-rw-r--r--panels/network/connection-editor/ce-page-ip6.c4
-rw-r--r--panels/network/connection-editor/ce-page.c120
-rw-r--r--panels/network/connection-editor/ce-page.h8
-rw-r--r--panels/network/connection-editor/ethernet-page.ui315
-rw-r--r--panels/network/connection-editor/net-connection-editor.c61
-rw-r--r--panels/network/net-device-ethernet.c451
-rw-r--r--panels/network/net-device-ethernet.h15
-rw-r--r--panels/network/network-ethernet.ui211
-rw-r--r--panels/network/network-simple.ui374
-rw-r--r--panels/network/panel-common.c18
-rw-r--r--panels/network/panel-common.h3
19 files changed, 2050 insertions, 220 deletions
diff --git a/panels/network/Makefile.am b/panels/network/Makefile.am
index dee5a004a..6785f6158 100644
--- a/panels/network/Makefile.am
+++ b/panels/network/Makefile.am
@@ -56,6 +56,7 @@ dist_ui_DATA = \
network-wifi.ui \
network-simple.ui \
network-mobile.ui \
+ network-ethernet.ui \
network.ui
@INTLTOOL_DESKTOP_RULE@
diff --git a/panels/network/connection-editor/Makefile.am b/panels/network/connection-editor/Makefile.am
index 06e83f9fa..1755203ae 100644
--- a/panels/network/connection-editor/Makefile.am
+++ b/panels/network/connection-editor/Makefile.am
@@ -16,7 +16,11 @@ libconnection_editor_la_SOURCES = \
ce-page-security.h \
ce-page-security.c \
ce-page-reset.h \
- ce-page-reset.c
+ ce-page-reset.c \
+ ce-page-ethernet.h \
+ ce-page-ethernet.c \
+ ce-page-8021x-security.h \
+ ce-page-8021x-security.c
libconnection_editor_la_CPPFLAGS = \
-I$(srcdir)/../wireless-security \
@@ -37,7 +41,8 @@ ui_DATA = \
ip4-page.ui \
ip6-page.ui \
reset-page.ui \
- security-page.ui
+ security-page.ui \
+ ethernet-page.ui
EXTRA_DIST = \
$(ui_DATA)
diff --git a/panels/network/connection-editor/ce-page-8021x-security.c b/panels/network/connection-editor/ce-page-8021x-security.c
new file mode 100644
index 000000000..ed716c8b4
--- /dev/null
+++ b/panels/network/connection-editor/ce-page-8021x-security.c
@@ -0,0 +1,188 @@
+/* -*- Mode: C; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*- */
+/* NetworkManager Connection editor -- Connection editor for NetworkManager
+ *
+ * Dan Williams <dcbw@redhat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * (C) Copyright 2008 - 2012 Red Hat, Inc.
+ */
+
+#include "config.h"
+
+#include <string.h>
+
+#include <gtk/gtk.h>
+#include <glib/gi18n.h>
+
+#include <NetworkManager.h>
+#include <nm-setting-connection.h>
+#include <nm-setting-wired.h>
+#include <nm-setting-8021x.h>
+#include <nm-setting-wireless.h>
+#include <nm-utils.h>
+
+#include "wireless-security.h"
+#include "ce-page-ethernet.h"
+#include "ce-page-8021x-security.h"
+
+G_DEFINE_TYPE (CEPage8021xSecurity, ce_page_8021x_security, CE_TYPE_PAGE)
+
+static void
+enable_toggled (GtkToggleButton *button, gpointer user_data)
+{
+ CEPage8021xSecurity *page = CE_PAGE_8021X_SECURITY (user_data);
+
+ gtk_widget_set_sensitive (page->security_widget, gtk_toggle_button_get_active (page->enabled));
+ ce_page_changed (CE_PAGE (page));
+}
+
+static void
+stuff_changed (WirelessSecurity *sec, gpointer user_data)
+{
+ ce_page_changed (CE_PAGE (user_data));
+}
+
+static void
+finish_setup (CEPage8021xSecurity *self, gpointer unused, GError *error, gpointer user_data)
+{
+ GtkWidget *parent;
+
+ if (error)
+ return;
+
+ self->security = (WirelessSecurity *) ws_wpa_eap_new (CE_PAGE (self)->connection, TRUE, FALSE);
+ if (!self->security) {
+ g_warning ("Could not load 802.1x user interface.");
+ return;
+ }
+
+ wireless_security_set_changed_notify (self->security, stuff_changed, self);
+ self->security_widget = wireless_security_get_widget (self->security);
+ parent = gtk_widget_get_parent (self->security_widget);
+ if (parent)
+ gtk_container_remove (GTK_CONTAINER (parent), self->security_widget);
+
+ gtk_toggle_button_set_active (self->enabled, self->initial_have_8021x);
+ g_signal_connect (self->enabled, "toggled", G_CALLBACK (enable_toggled), self);
+ gtk_widget_set_sensitive (self->security_widget, self->initial_have_8021x);
+
+ gtk_box_pack_start (GTK_BOX (CE_PAGE (self)->page), GTK_WIDGET (self->enabled), FALSE, TRUE, 12);
+ gtk_box_pack_start (GTK_BOX (CE_PAGE (self)->page), self->security_widget, TRUE, TRUE, 0);
+ gtk_widget_show_all (CE_PAGE (self)->page);
+}
+
+CEPage *
+ce_page_8021x_security_new (NMConnection *connection,
+ NMClient *client,
+ NMRemoteSettings *settings)
+{
+ CEPage8021xSecurity *self;
+
+ self = CE_PAGE_8021X_SECURITY (ce_page_new (CE_TYPE_PAGE_8021X_SECURITY,
+ connection,
+ client,
+ settings,
+ NULL,
+ _("Security")));
+
+ CE_PAGE (self)->page = gtk_box_new (GTK_ORIENTATION_VERTICAL, 6);
+
+ g_object_ref_sink (G_OBJECT (CE_PAGE (self)->page));
+ gtk_container_set_border_width (GTK_CONTAINER (CE_PAGE (self)->page), 6);
+
+ if (nm_connection_get_setting_802_1x (connection))
+ self->initial_have_8021x = TRUE;
+
+ self->enabled = GTK_TOGGLE_BUTTON (gtk_check_button_new_with_mnemonic (_("Use 802.1_X security for this connection")));
+
+ g_signal_connect (self, "initialized", G_CALLBACK (finish_setup), NULL);
+
+ if (self->initial_have_8021x)
+ CE_PAGE (self)->security_setting = NM_SETTING_802_1X_SETTING_NAME;
+
+ return CE_PAGE (self);
+}
+
+static gboolean
+validate (CEPage *page, NMConnection *connection, GError **error)
+{
+ CEPage8021xSecurity *self = CE_PAGE_8021X_SECURITY (page);
+ gboolean valid = TRUE;
+
+ if (gtk_toggle_button_get_active (self->enabled)) {
+ NMConnection *tmp_connection;
+ NMSetting *s_8021x;
+
+ /* FIXME: get failed property and error out of wireless security objects */
+ valid = wireless_security_validate (self->security, NULL);
+ if (valid) {
+ NMSetting *s_con;
+
+ /* Here's a nice hack to work around the fact that ws_802_1x_fill_connection needs wireless setting. */
+ tmp_connection = nm_connection_new ();
+ nm_connection_add_setting (tmp_connection, nm_setting_wireless_new ());
+
+ /* temp connection needs a 'connection' setting too, since most of
+ * the EAP methods need the UUID for CA cert ignore stuff.
+ */
+ s_con = nm_connection_get_setting (connection, NM_TYPE_SETTING_CONNECTION);
+ nm_connection_add_setting (tmp_connection, nm_setting_duplicate (s_con));
+
+ ws_802_1x_fill_connection (self->security, "wpa_eap_auth_combo", tmp_connection);
+
+ s_8021x = nm_connection_get_setting (tmp_connection, NM_TYPE_SETTING_802_1X);
+ nm_connection_add_setting (connection, NM_SETTING (g_object_ref (s_8021x)));
+
+ g_object_unref (tmp_connection);
+ } else
+ g_set_error (error, NM_CONNECTION_ERROR, NM_CONNECTION_ERROR_UNKNOWN, "Invalid 802.1x security");
+ } else {
+ nm_connection_remove_setting (connection, NM_TYPE_SETTING_802_1X);
+ valid = TRUE;
+ }
+
+ return valid;
+}
+
+static void
+ce_page_8021x_security_init (CEPage8021xSecurity *self)
+{
+}
+
+static void
+dispose (GObject *object)
+{
+ CEPage8021xSecurity *self = CE_PAGE_8021X_SECURITY (object);
+
+ if (self->security) {
+ wireless_security_unref (self->security);
+ self->security = NULL;
+ }
+
+ G_OBJECT_CLASS (ce_page_8021x_security_parent_class)->dispose (object);
+}
+
+static void
+ce_page_8021x_security_class_init (CEPage8021xSecurityClass *security_class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (security_class);
+ CEPageClass *parent_class = CE_PAGE_CLASS (security_class);
+
+ /* virtual methods */
+ object_class->dispose = dispose;
+
+ parent_class->validate = validate;
+}
diff --git a/panels/network/connection-editor/ce-page-8021x-security.h b/panels/network/connection-editor/ce-page-8021x-security.h
new file mode 100644
index 000000000..1432b0e10
--- /dev/null
+++ b/panels/network/connection-editor/ce-page-8021x-security.h
@@ -0,0 +1,64 @@
+/* -*- Mode: C; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*- */
+/* NetworkManager Connection editor -- Connection editor for NetworkManager
+ *
+ * Dan Williams <dcbw@redhat.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * (C) Copyright 2008 - 2012 Red Hat, Inc.
+ */
+
+#ifndef __CE_PAGE_8021X_SECURITY_H
+#define __CE_PAGE_8021X_SECURITY_H
+
+#include <nm-connection.h>
+#include "wireless-security.h"
+
+#include <glib.h>
+#include <glib-object.h>
+
+#include "ce-page.h"
+
+#define CE_TYPE_PAGE_8021X_SECURITY (ce_page_8021x_security_get_type ())
+#define CE_PAGE_8021X_SECURITY(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), CE_TYPE_PAGE_8021X_SECURITY, CEPage8021xSecurity))
+#define CE_PAGE_8021X_SECURITY_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), CE_TYPE_PAGE_8021X_SECURITY, CEPage8021xSecurityClass))
+#define CE_IS_PAGE_8021X_SECURITY(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), CE_TYPE_PAGE_8021X_SECURITY))
+#define CE_IS_PAGE_8021X_SECURITY_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), CE_TYPE_PAGE_8021X_SECURITY))
+#define CE_PAGE_8021X_SECURITY_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), CE_TYPE_PAGE_8021X_SECURITY, CEPage8021xSecurityClass))
+
+typedef struct CEPage8021xSecurity CEPage8021xSecurity;
+typedef struct CEPage8021xSecurityClass CEPage8021xSecurityClass;
+
+struct CEPage8021xSecurity {
+ CEPage parent;
+
+ GtkToggleButton *enabled;
+ GtkWidget *security_widget;
+ WirelessSecurity *security;
+
+ gboolean initial_have_8021x;
+};
+
+struct CEPage8021xSecurityClass {
+ CEPageClass parent;
+};
+
+GType ce_page_8021x_security_get_type (void);
+
+CEPage *ce_page_8021x_security_new (NMConnection *connection,
+ NMClient *client,
+ NMRemoteSettings *settings);
+
+#endif /* __CE_PAGE_8021X_SECURITY_H */
diff --git a/panels/network/connection-editor/ce-page-details.c b/panels/network/connection-editor/ce-page-details.c
index 0beb55ff8..ff8edb4df 100644
--- a/panels/network/connection-editor/ce-page-details.c
+++ b/panels/network/connection-editor/ce-page-details.c
@@ -26,6 +26,7 @@
#include <nm-utils.h>
#include <nm-device-wifi.h>
+#include <nm-device-ethernet.h>
#include "../panel-common.h"
#include "ce-page-details.h"
@@ -136,6 +137,7 @@ connect_details_page (CEPageDetails *page)
NMDeviceState state;
NMAccessPoint *active_ap;
const gchar *str;
+ gboolean device_is_active;
widget = GTK_WIDGET (gtk_builder_get_object (CE_PAGE (page)->builder,
"auto_connect_switch"));
@@ -150,12 +152,33 @@ connect_details_page (CEPageDetails *page)
g_signal_connect (widget, "notify::active",
G_CALLBACK (all_user_changed), page);
- active_ap = nm_device_wifi_get_active_access_point (NM_DEVICE_WIFI (page->device));
+ if (NM_IS_DEVICE_WIFI (page->device))
+ active_ap = nm_device_wifi_get_active_access_point (NM_DEVICE_WIFI (page->device));
+ else
+ active_ap = NULL;
+
state = nm_device_get_state (page->device);
+ device_is_active = FALSE;
speed = 0;
- if (page->ap == active_ap && state != NM_DEVICE_STATE_UNAVAILABLE) {
- speed = nm_device_wifi_get_bitrate (NM_DEVICE_WIFI (page->device)) / 1000;
+ if (active_ap && page->ap == active_ap && state != NM_DEVICE_STATE_UNAVAILABLE) {
+ device_is_active = TRUE;
+ if (NM_IS_DEVICE_WIFI (page->device))
+ speed = nm_device_wifi_get_bitrate (NM_DEVICE_WIFI (page->device)) / 1000;
+ } else {
+ NMActiveConnection *ac;
+ const gchar *p1, *p2;
+
+ ac = nm_device_get_active_connection (page->device);
+ p1 = ac ? nm_active_connection_get_connection (ac) : NULL;
+ p2 = nm_connection_get_path (CE_PAGE (page)->connection);
+ if (g_strcmp0 (p1, p2) == 0) {
+ device_is_active = TRUE;
+ if (NM_IS_DEVICE_WIFI (page->device))
+ speed = nm_device_wifi_get_bitrate (NM_DEVICE_WIFI (page->device)) / 1000;
+ else if (NM_IS_DEVICE_ETHERNET (page->device))
+ speed = nm_device_ethernet_get_speed (NM_DEVICE_ETHERNET (page->device));
+ }
}
if (speed > 0)
str = g_strdup_printf (_("%d Mb/s"), speed);
@@ -163,11 +186,15 @@ connect_details_page (CEPageDetails *page)
str = NULL;
panel_set_device_widget_details (CE_PAGE (page)->builder, "speed", str);
- str = nm_device_wifi_get_hw_address (NM_DEVICE_WIFI (page->device));
+ if (NM_IS_DEVICE_WIFI (page->device))
+ str = nm_device_wifi_get_hw_address (NM_DEVICE_WIFI (page->device));
+ else if (NM_IS_DEVICE_ETHERNET (page->device))
+ str = nm_device_ethernet_get_hw_address (NM_DEVICE_ETHERNET (page->device));
+
panel_set_device_widget_details (CE_PAGE (page)->builder, "mac", str);
str = NULL;
- if (page->ap == active_ap)
+ if (device_is_active && active_ap)
str = get_ap_security_string (active_ap);
panel_set_device_widget_details (CE_PAGE (page)->builder, "security", str);
@@ -190,12 +217,12 @@ connect_details_page (CEPageDetails *page)
panel_set_device_widget_details (CE_PAGE (page)->builder, "strength", str);
/* set IP entries */
- if (page->ap != active_ap)
- panel_unset_device_widgets (CE_PAGE (page)->builder);
- else
+ if (device_is_active)
panel_set_device_widgets (CE_PAGE (page)->builder, page->device);
+ else
+ panel_unset_device_widgets (CE_PAGE (page)->builder);
- if (page->ap != active_ap && CE_PAGE (page)->connection)
+ if (!device_is_active && CE_PAGE (page)->connection)
update_last_used (page, CE_PAGE (page)->connection);
else
panel_set_device_widget_details (CE_PAGE (page)->builder, "last_used", NULL);
diff --git a/panels/network/connection-editor/ce-page-ethernet.c b/panels/network/connection-editor/ce-page-ethernet.c
new file mode 100644
index 000000000..d11b7cbe1
--- /dev/null
+++ b/panels/network/connection-editor/ce-page-ethernet.c
@@ -0,0 +1,304 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
+ *
+ * Copyright (C) 2012 Red Hat, Inc
+ *
+ * Licensed under the GNU General Public License Version 2
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+#include "config.h"
+
+#include <glib-object.h>
+#include <glib/gi18n.h>
+
+#include <nm-utils.h>
+#include <nm-device-ethernet.h>
+
+#include <net/if_arp.h>
+
+#include "ce-page-ethernet.h"
+
+G_DEFINE_TYPE (CEPageEthernet, ce_page_ethernet, CE_TYPE_PAGE)
+
+enum {
+ PORT_DEFAULT,
+ PORT_TP,
+ PORT_AUI,
+ PORT_BNC,
+ PORT_MII
+};
+
+enum {
+ SPEED_DEFAULT,
+ SPEED_10,
+ SPEED_100,
+ SPEED_1000,
+ SPEED_10000
+};
+
+static void
+connect_ethernet_page (CEPageEthernet *page)
+{
+ NMSettingWired *setting = page->setting_wired;
+ const char *port;
+ const char *duplex;
+ int port_idx = PORT_DEFAULT;
+ int speed_idx;
+ int mtu_def;
+ char **mac_list;
+ const GByteArray *s_mac;
+ char *s_mac_str;
+ GtkWidget *widget;
+ const gchar *name;
+
+ name = nm_setting_connection_get_id (page->setting_connection);
+ gtk_entry_set_text (page->name, name);
+
+ /* Port */
+ port = nm_setting_wired_get_port (setting);
+ if (port) {
+ if (!strcmp (port, "tp"))
+ port_idx = PORT_TP;
+ else if (!strcmp (port, "aui"))
+ port_idx = PORT_AUI;
+ else if (!strcmp (port, "bnc"))
+ port_idx = PORT_BNC;
+ else if (!strcmp (port, "mii"))
+ port_idx = PORT_MII;
+ }
+ gtk_combo_box_set_active (page->port, port_idx);
+
+ /* Speed */
+ switch (nm_setting_wired_get_speed (setting)) {
+ case 10:
+ speed_idx = SPEED_10;
+ break;
+ case 100:
+ speed_idx = SPEED_100;
+ break;
+ case 1000:
+ speed_idx = SPEED_1000;
+ break;
+ case 10000:
+ speed_idx = SPEED_10000;
+ break;
+ default:
+ speed_idx = SPEED_DEFAULT;
+ break;
+ }
+ gtk_combo_box_set_active (page->speed, speed_idx);
+ /* Duplex */
+ duplex = nm_setting_wired_get_duplex (setting);
+ if (duplex && !strcmp (duplex, "half"))
+ gtk_toggle_button_set_active (page->duplex, FALSE);
+ else
+ gtk_toggle_button_set_active (page->duplex, TRUE);
+
+ /* Autonegotiate */
+ gtk_toggle_button_set_active (page->autonegotiate,
+ nm_setting_wired_get_auto_negotiate (setting));
+
+ /* Device MAC address */
+ mac_list = ce_page_get_mac_list (CE_PAGE (page)->client, NM_TYPE_DEVICE_ETHERNET,
+ NM_DEVICE_ETHERNET_PERMANENT_HW_ADDRESS);
+ s_mac = nm_setting_wired_get_mac_address (setting);
+ s_mac_str = s_mac ? nm_utils_hwaddr_ntoa (s_mac->data, ARPHRD_ETHER) : NULL;
+ ce_page_setup_mac_combo (page->device_mac, s_mac_str, mac_list);
+ g_free (s_mac_str);
+ g_strfreev (mac_list);
+ g_signal_connect_swapped (page->device_mac, "changed", G_CALLBACK (ce_page_changed), page);
+
+ /* Cloned MAC address */
+ ce_page_mac_to_entry (nm_setting_wired_get_cloned_mac_address (setting),
+ ARPHRD_ETHER, page->cloned_mac);
+ g_signal_connect_swapped (page->cloned_mac, "changed", G_CALLBACK (ce_page_changed), page);
+
+ /* MTU */
+ mtu_def = ce_get_property_default (NM_SETTING (setting), NM_SETTING_WIRED_MTU);
+ g_signal_connect (page->mtu, "output",
+ G_CALLBACK (ce_spin_output_with_default),
+ GINT_TO_POINTER (mtu_def));
+
+ gtk_spin_button_set_value (page->mtu, (gdouble) nm_setting_wired_get_mtu (setting));
+
+ g_signal_connect_swapped (page->name, "changed", G_CALLBACK (ce_page_changed), page);
+ g_signal_connect_swapped (page->port, "changed", G_CALLBACK (ce_page_changed), page);
+ g_signal_connect_swapped (page->speed, "changed", G_CALLBACK (ce_page_changed), page);
+ g_signal_connect_swapped (page->duplex, "toggled", G_CALLBACK (ce_page_changed), page);
+ g_signal_connect_swapped (page->autonegotiate, "toggled", G_CALLBACK (ce_page_changed), page);
+ g_signal_connect_swapped (page->mtu, "value-changed", G_CALLBACK (ce_page_changed), page);
+
+ /* Hide widgets we don't yet support */
+ widget = GTK_WIDGET (gtk_builder_get_object (CE_PAGE (page)->builder, "heading_port"));
+ gtk_widget_hide (widget);
+ gtk_widget_hide (GTK_WIDGET (page->port));
+
+ widget = GTK_WIDGET (gtk_builder_get_object (CE_PAGE (page)->builder, "heading_speed"));
+ gtk_widget_hide (widget);
+ gtk_widget_hide (GTK_WIDGET (page->speed));
+
+ widget = GTK_WIDGET (gtk_builder_get_object (CE_PAGE (page)->builder, "check_duplex"));
+ gtk_widget_hide (widget);
+ widget = GTK_WIDGET (gtk_builder_get_object (CE_PAGE (page)->builder, "check_renegotiate"));
+ gtk_widget_hide (widget);
+}
+
+static void
+ui_to_setting (CEPageEthernet *page)
+{
+ const char *port;
+ guint32 speed;
+ GByteArray *device_mac = NULL;
+ GByteArray *cloned_mac = NULL;
+ GtkWidget *entry;
+
+ /* Port */
+ switch (gtk_combo_box_get_active (page->port)) {
+ case PORT_TP:
+ port = "tp";
+ break;
+ case PORT_AUI:
+ port = "aui";
+ break;
+ case PORT_BNC:
+ port = "bnc";
+ break;
+ case PORT_MII:
+ port = "mii";
+ break;
+ default:
+ port = NULL;
+ break;
+ }
+
+ /* Speed */
+ switch (gtk_combo_box_get_active (page->speed)) {
+ case SPEED_10:
+ speed = 10;
+ break;
+ case SPEED_100:
+ speed = 100;
+ break;
+ case SPEED_1000:
+ speed = 1000;
+ break;
+ case SPEED_10000:
+ speed = 10000;
+ break;
+ default:
+ speed = 0;
+ break;
+ }
+
+ entry = gtk_bin_get_child (GTK_BIN (page->device_mac));
+ if (entry)
+ device_mac = ce_page_entry_to_mac (GTK_ENTRY (entry), ARPHRD_ETHER, NULL);
+ cloned_mac = ce_page_entry_to_mac (page->cloned_mac, ARPHRD_ETHER, NULL);
+
+ g_object_set (page->setting_wired,
+ NM_SETTING_WIRED_MAC_ADDRESS, device_mac,
+ NM_SETTING_WIRED_CLONED_MAC_ADDRESS, cloned_mac,
+ NM_SETTING_WIRED_PORT, port,
+ NM_SETTING_WIRED_SPEED, speed,
+ NM_SETTING_WIRED_DUPLEX, gtk_toggle_button_get_active (page->duplex) ? "full" : "half",
+ NM_SETTING_WIRED_AUTO_NEGOTIATE, gtk_toggle_button_get_active (page->autonegotiate),
+ NM_SETTING_WIRED_MTU, (guint32) gtk_spin_button_get_value_as_int (page->mtu),
+ NULL);
+
+ if (device_mac)
+ g_byte_array_free (device_mac, TRUE);
+ if (cloned_mac)
+ g_byte_array_free (cloned_mac, TRUE);
+
+ g_object_set (page->setting_connection,
+ NM_SETTING_CONNECTION_ID, gtk_entry_get_text (page->name),
+ NULL);
+}
+
+static gboolean
+validate (CEPage *page,
+ NMConnection *connection,
+ GError **error)
+{
+ CEPageEthernet *self = CE_PAGE_ETHERNET (page);
+ gboolean invalid = FALSE;
+ GByteArray *ignore;
+ GtkWidget *entry;
+
+ entry = gtk_bin_get_child (GTK_BIN (self->device_mac));
+ if (entry) {
+ ignore = ce_page_entry_to_mac (GTK_ENTRY (entry), ARPHRD_ETHER, &invalid);
+ if (invalid)
+ return FALSE;
+ if (ignore)
+ g_byte_array_free (ignore, TRUE);
+ }
+
+ ignore = ce_page_entry_to_mac (self->cloned_mac, ARPHRD_ETHER, &invalid);
+ if (invalid)
+ return FALSE;
+ if (ignore)
+ g_byte_array_free (ignore, TRUE);
+
+ ui_to_setting (self);
+
+ return nm_setting_verify (NM_SETTING (self->setting_connection), NULL, error) &&
+ nm_setting_verify (NM_SETTING (self->setting_wired), NULL, error);
+}
+
+static void
+ce_page_ethernet_init (CEPageEthernet *page)
+{
+}
+
+static void
+ce_page_ethernet_class_init (CEPageEthernetClass *class)
+{
+ CEPageClass *page_class= CE_PAGE_CLASS (class);
+
+ page_class->validate = validate;
+}
+
+CEPage *
+ce_page_ethernet_new (NMConnection *connection,
+ NMClient *client,
+ NMRemoteSettings *settings)
+{
+ CEPageEthernet *page;
+
+ page = CE_PAGE_ETHERNET (ce_page_new (CE_TYPE_PAGE_ETHERNET,
+ connection,
+ client,
+ settings,
+ GNOMECC_UI_DIR "/ethernet-page.ui",
+ _("Identity")));
+
+ page->name = GTK_ENTRY (gtk_builder_get_object (CE_PAGE (page)->builder, "entry_name"));
+ page->device_mac = GTK_COMBO_BOX_TEXT (gtk_builder_get_object (CE_PAGE (page)->builder, "combo_mac"));
+ page->cloned_mac = GTK_ENTRY (gtk_builder_get_object (CE_PAGE (page)->builder, "entry_cloned_mac"));
+ page->port = GTK_COMBO_BOX (gtk_builder_get_object (CE_PAGE (page)->builder, "combo_port"));
+ page->speed = GTK_COMBO_BOX (gtk_builder_get_object (CE_PAGE (page)->builder, "combo_speed"));
+ page->duplex = GTK_TOGGLE_BUTTON (gtk_builder_get_object (CE_PAGE (page)->builder, "check_duplex"));
+ page->autonegotiate = GTK_TOGGLE_BUTTON (gtk_builder_get_object (CE_PAGE (page)->builder, "check_renegotiate"));
+ page->mtu = GTK_SPIN_BUTTON (gtk_builder_get_object (CE_PAGE (page)->builder, "spin_mtu"));
+
+ page->setting_connection = nm_connection_get_setting_connection (connection);
+ page->setting_wired = nm_connection_get_setting_wired (connection);
+
+ connect_ethernet_page (page);
+
+ return CE_PAGE (page);
+}
diff --git a/panels/network/connection-editor/ce-page-ethernet.h b/panels/network/connection-editor/ce-page-ethernet.h
new file mode 100644
index 000000000..3f0942e43
--- /dev/null
+++ b/panels/network/connection-editor/ce-page-ethernet.h
@@ -0,0 +1,75 @@
+/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
+ *
+ * Copyright (C) 2012 Red Hat, Inc.
+ *
+ * Licensed under the GNU General Public License Version 2
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more ethernet.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+#ifndef __CE_PAGE_ETHERNET_H
+#define __CE_PAGE_ETHERNET_H
+
+#include <glib-object.h>
+
+#include <nm-setting-wired.h>
+
+#include <gtk/gtk.h>
+#include "ce-page.h"
+
+G_BEGIN_DECLS
+
+#define CE_TYPE_PAGE_ETHERNET (ce_page_ethernet_get_type ())
+#define CE_PAGE_ETHERNET(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), CE_TYPE_PAGE_ETHERNET, CEPageEthernet))
+#define CE_PAGE_ETHERNET_CLASS(k) (G_TYPE_CHECK_CLASS_CAST((k), CE_TYPE_PAGE_ETHERNET, CEPageEthernetClass))
+#define CE_IS_PAGE_ETHERNET(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), CE_TYPE_PAGE_ETHERNET))
+#define CE_IS_PAGE_ETHERNET_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), CE_TYPE_PAGE_ETHERNET))
+#define CE_PAGE_ETHERNET_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), CE_TYPE_PAGE_ETHERNET, CEPageEthernetClass))
+
+typedef struct _CEPageEthernet CEPageEthernet;
+typedef struct _CEPageEthernetClass CEPageEthernetClass;
+
+struct _CEPageEthernet
+{
+ CEPage parent;
+
+ NMSettingConnection *setting_connection;
+ NMSettingWired *setting_wired;
+
+ GtkEntry *name;
+ GtkComboBoxText *device_mac;
+ GtkEntry *cloned_mac;
+ GtkComboBox *port;
+ GtkComboBox *speed;
+ GtkToggleButton *duplex;
+ GtkToggleButton *autonegotiate;
+ GtkSpinButton *mtu;
+};
+
+struct _CEPageEthernetClass
+{
+ CEPageClass parent_class;
+};
+
+GType ce_page_ethernet_get_type (void);
+
+CEPage *ce_page_ethernet_new (NMConnection *connection,
+ NMClient *client,
+ NMRemoteSettings *settings);
+
+G_END_DECLS
+
+#endif /* __CE_PAGE_ETHERNET_H */
+
diff --git a/panels/network/connection-editor/ce-page-ip4.c b/panels/network/connection-editor/ce-page-ip4.c
index 7a7e862eb..5cdb08040 100644
--- a/panels/network/connection-editor/ce-page-ip4.c
+++ b/panels/network/connection-editor/ce-page-ip4.c
@@ -894,6 +894,10 @@ ce_page_ip4_new (NMConnection *connection,
_("IPv4")));
page->setting = nm_connection_get_setting_ip4_config (connection);
+ if (!page->setting) {
+ page->setting = NM_SETTING_IP4_CONFIG (nm_setting_ip4_config_new ());
+ nm_connection_add_setting (connection, NM_SETTING (page->setting));
+ }
connect_ip4_page (page);
diff --git a/panels/network/connection-editor/ce-page-ip6.c b/panels/network/connection-editor/ce-page-ip6.c
index 06c0214cf..099d2071b 100644
--- a/panels/network/connection-editor/ce-page-ip6.c
+++ b/panels/network/connection-editor/ce-page-ip6.c
@@ -855,6 +855,10 @@ ce_page_ip6_new (NMConnection *connection,
_("IPv6")));
page->setting = nm_connection_get_setting_ip6_config (connection);
+ if (!page->setting) {
+ page->setting = NM_SETTING_IP6_CONFIG (nm_setting_ip6_config_new ());
+ nm_connection_add_setting (connection, NM_SETTING (page->setting));
+ }
connect_ip6_page (page);
diff --git a/panels/network/connection-editor/ce-page.c b/panels/network/connection-editor/ce-page.c
index 4794a5fda..f6c1f4013 100644
--- a/panels/network/connection-editor/ce-page.c
+++ b/panels/network/connection-editor/ce-page.c
@@ -28,6 +28,8 @@
#include <nm-utils.h>
+#include <glib/gi18n.h>
+
#include "ce-page.h"
@@ -224,20 +226,23 @@ ce_page_new (GType type,
page->title = g_strdup (title);
page->client = client;
page->settings= settings;
- if (!gtk_builder_add_from_file (page->builder, ui_file, &error)) {
- g_warning ("Couldn't load builder file: %s", error->message);
- g_error_free (error);
- g_object_unref (page);
- return NULL;
- }
- page->page = GTK_WIDGET (gtk_builder_get_object (page->builder, "page"));
- if (!page->page) {
- g_warning ("Couldn't load page widget from %s", ui_file);
- g_object_unref (page);
- return NULL;
- }
- g_object_ref_sink (page->page);
+ if (ui_file) {
+ if (!gtk_builder_add_from_file (page->builder, ui_file, &error)) {
+ g_warning ("Couldn't load builder file: %s", error->message);
+ g_error_free (error);
+ g_object_unref (page);
+ return NULL;
+ }
+ page->page = GTK_WIDGET (gtk_builder_get_object (page->builder, "page"));
+ if (!page->page) {
+ g_warning ("Couldn't load page widget from %s", ui_file);
+ g_object_unref (page);
+ return NULL;
+ }
+
+ g_object_ref_sink (page->page);
+ }
return page;
}
@@ -452,3 +457,92 @@ ce_page_get_security_setting (CEPage *page)
{
return page->security_setting;
}
+
+gint
+ce_get_property_default (NMSetting *setting, const gchar *property_name)
+{
+ GParamSpec *spec;
+ GValue value = { 0, };
+
+ spec = g_object_class_find_property (G_OBJECT_GET_CLASS (setting), property_name);
+ g_return_val_if_fail (spec != NULL, -1);
+
+ g_value_init (&value, spec->value_type);
+ g_param_value_set_default (spec, &value);
+
+ if (G_VALUE_HOLDS_CHAR (&value))
+ return (int) g_value_get_schar (&value);
+ else if (G_VALUE_HOLDS_INT (&value))
+ return g_value_get_int (&value);
+ else if (G_VALUE_HOLDS_INT64 (&value))
+ return (int) g_value_get_int64 (&value);
+ else if (G_VALUE_HOLDS_LONG (&value))
+ return (int) g_value_get_long (&value);
+ else if (G_VALUE_HOLDS_UINT (&value))
+ return (int) g_value_get_uint (&value);
+ else if (G_VALUE_HOLDS_UINT64 (&value))
+ return (int) g_value_get_uint64 (&value);
+ else if (G_VALUE_HOLDS_ULONG (&value))
+ return (int) g_value_get_ulong (&value);
+ else if (G_VALUE_HOLDS_UCHAR (&value))
+ return (int) g_value_get_uchar (&value);
+ g_return_val_if_fail (FALSE, 0);
+ return 0;
+}
+
+gint
+ce_spin_output_with_default (GtkSpinButton *spin, gpointer user_data)
+{
+ gint defvalue = GPOINTER_TO_INT (user_data);
+ gint val;
+ gchar *buf = NULL;
+
+ val = gtk_spin_button_get_value_as_int (spin);
+ if (val == defvalue)
+ buf = g_strdup (_("automatic"));
+ else
+ buf = g_strdup_printf ("%d", val);
+
+ if (strcmp (buf, gtk_entry_get_text (GTK_ENTRY (spin))))
+ gtk_entry_set_text (GTK_ENTRY (spin), buf);
+
+ g_free (buf);
+ return TRUE;
+}
+
+gchar *
+ce_page_get_next_available_name (GSList *connections, const gchar *format)
+{
+ GSList *names = NULL, *l;
+ gchar *cname = NULL;
+ gint i = 0;
+
+ for (l = connections; l; l = l->next) {
+ const gchar *id;
+
+ id = nm_connection_get_id (NM_CONNECTION (l->data));
+ g_assert (id);
+ names = g_slist_append (names, (gpointer) id);
+ }
+
+ /* Find the next available unique connection name */
+ while (!cname && (i++ < 10000)) {
+ gchar *temp;
+ gboolean found = FALSE;
+
+ temp = g_strdup_printf (format, i);
+ for (l = names; l; l = l->next) {
+ if (!strcmp (l->data, temp)) {
+ found = TRUE;
+ break;
+ }
+ }
+ if (!found)
+ cname = temp;
+ else
+ g_free (temp);
+ }
+ g_slist_free (names);
+
+ return cname;
+}
diff --git a/panels/network/connection-editor/ce-page.h b/panels/network/connection-editor/ce-page.h
index 2de2adafd..58cd41d9b 100644
--- a/panels/network/connection-editor/ce-page.h
+++ b/panels/network/connection-editor/ce-page.h
@@ -99,6 +99,14 @@ void ce_page_mac_to_entry (const GByteArray *mac,
GByteArray *ce_page_entry_to_mac (GtkEntry *entry,
gint type,
gboolean *invalid);
+gint ce_get_property_default (NMSetting *setting,
+ const gchar *property_name);
+gint ce_spin_output_with_default (GtkSpinButton *spin,
+ gpointer user_data);
+
+gchar * ce_page_get_next_available_name (GSList *connections, const gchar *format);
+
+
G_END_DECLS
diff --git a/panels/network/connection-editor/ethernet-page.ui b/panels/network/connection-editor/ethernet-page.ui
new file mode 100644
index 000000000..477b0ad1e
--- /dev/null
+++ b/panels/network/connection-editor/ethernet-page.ui
@@ -0,0 +1,315 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<interface>
+ <!-- interface-requires gtk+ 3.0 -->
+ <object class="GtkAdjustment" id="adjustment1">
+ <property name="upper">10000</property>
+ <property name="step_increment">1</property>
+ <property name="page_increment">10</property>
+ </object>
+ <object class="GtkListStore" id="model1">
+ <columns>
+ <!-- column-name gchararray1 -->
+ <column type="gchararray"/>
+ </columns>
+ <data>
+ <row>
+ <col id="0" translatable="yes">Automatic</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">Twisted Pair (TP)</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">Attachment Unit Interface (AUI)</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">BNC</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">Media Independent Interface (MII)</col>
+ </row>
+ </data>
+ </object>
+ <object class="GtkListStore" id="model2">
+ <columns>
+ <!-- column-name < -->
+ <column type="gchararray"/>
+ </columns>
+ <data>
+ <row>
+ <col id="0" translatable="yes">Automatic</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">10 Mb/s</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">100 Mb/s</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">1 Gb/s</col>
+ </row>
+ <row>
+ <col id="0" translatable="yes">10 Gb/s</col>
+ </row>
+ </data>
+ </object>
+ <object class="GtkGrid" id="page">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="margin_left">50</property>
+ <property name="margin_right">50</property>
+ <property name="margin_top">12</property>
+ <property name="margin_bottom">12</property>
+ <property name="hexpand">True</property>
+ <property name="vexpand">True</property>
+ <property name="row_spacing">10</property>
+ <property name="column_spacing">6</property>
+ <child>
+ <object class="GtkLabel" id="heading_mtu">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">_MTU</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">spin_mtu</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">7</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkBox" id="box1">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="spacing">6</property>
+ <child>
+ <object class="GtkSpinButton" id="spin_mtu">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="invisible_char">ā—</property>
+ <property name="adjustment">adjustment1</property>
+ </object>
+ <packing>
+ <property name="expand">True</property>
+ <property name="fill">True</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_mtu">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="label" translatable="yes">bytes</property>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">True</property>
+ <property name="position">2</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">7</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_cloned_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="label" translatable="yes">_Cloned MAC Address</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">entry_cloned_mac</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">6</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">_MAC Address</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">combo_mac</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">5</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkEntry" id="entry_cloned_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="hexpand">True</property>
+ <property name="invisible_char">ā—</property>
+ <property name="invisible_char_set">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">6</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkComboBoxText" id="combo_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="has_entry">True</property>
+ <property name="entry_text_column">0</property>
+ <property name="id_column">1</property>
+ <child internal-child="entry">
+ <object class="GtkEntry" id="comboboxtext-entry2">
+ <property name="can_focus">False</property>
+ <property name="invisible_char">ā—</property>
+ </object>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">5</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_port">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">_Port</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">combo_port</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">1</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_speed">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">_Speed</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">combo_speed</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">2</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkCheckButton" id="check_duplex">
+ <property name="label" translatable="yes">_Full duplex</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="xalign">0</property>
+ <property name="draw_indicator">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">3</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkCheckButton" id="check_renegotiate">
+ <property name="label" translatable="yes">_Automatic renegotiation</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="xalign">0</property>
+ <property name="draw_indicator">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">4</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkComboBox" id="combo_port">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="model">model1</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">1</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkComboBox" id="combo_speed">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="model">model2</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">2</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_name">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">Name</property>
+ <property name="use_underline">True</property>
+ <property name="mnemonic_widget">entry_name</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkEntry" id="entry_name">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="invisible_char">ā—</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <placeholder/>
+ </child>
+ <child>
+ <placeholder/>
+ </child>
+ </object>
+</interface>
diff --git a/panels/network/connection-editor/net-connection-editor.c b/panels/network/connection-editor/net-connection-editor.c
index b3d067239..b4b50346c 100644
--- a/panels/network/connection-editor/net-connection-editor.c
+++ b/panels/network/connection-editor/net-connection-editor.c
@@ -34,6 +34,8 @@
#include "ce-page-ip6.h"
#include "ce-page-security.h"
#include "ce-page-reset.h"
+#include "ce-page-ethernet.h"
+#include "ce-page-8021x-security.h"
#include "egg-list-box/egg-list-box.h"
@@ -87,7 +89,9 @@ update_complete (NetConnectionEditor *editor, GError *error)
}
static void
-updated_connection_cb (NMRemoteConnection *connection, GError *error, gpointer data)
+updated_connection_cb (NMRemoteConnection *connection,
+ GError *error,
+ gpointer data)
{
NetConnectionEditor *editor = data;
@@ -97,11 +101,36 @@ updated_connection_cb (NMRemoteConnection *connection, GError *error, gpointer d
}
static void
+added_connection_cb (NMRemoteSettings *settings,
+ NMRemoteConnection *connection,
+ GError *error,
+ gpointer data)
+{
+ NetConnectionEditor *editor = data;
+
+ if (error) {
+ g_warning ("Failed to add connection: %s", error->message);
+ /* Leave the editor open */
+ return;
+ }
+
+ update_complete (editor, error);
+}
+
+static void
apply_edits (NetConnectionEditor *editor)
{
update_connection (editor);
- nm_remote_connection_commit_changes (NM_REMOTE_CONNECTION (editor->orig_connection),
- updated_connection_cb, editor);
+
+ if (!nm_remote_settings_get_connection_by_uuid (editor->settings, nm_connection_get_uuid (editor->orig_connection)))
+ nm_remote_settings_add_connection (editor->settings,
+ editor->orig_connection,
+ added_connection_cb,
+ editor);
+ else {
+ nm_remote_connection_commit_changes (NM_REMOTE_CONNECTION (editor->orig_connection),
+ updated_connection_cb, editor);
+ }
}
static void
@@ -191,8 +220,12 @@ net_connection_editor_update_title (NetConnectionEditor *editor)
gchar *id;
sw = nm_connection_get_setting_wireless (editor->connection);
- ssid = nm_setting_wireless_get_ssid (sw);
- id = nm_utils_ssid_to_utf8 (ssid);
+ if (sw) {
+ ssid = nm_setting_wireless_get_ssid (sw);
+ id = nm_utils_ssid_to_utf8 (ssid);
+ } else {
+ id = g_strdup (nm_connection_get_id (editor->connection));
+ }
gtk_window_set_title (GTK_WINDOW (editor->window), id);
g_free (id);
}
@@ -385,17 +418,31 @@ net_connection_editor_set_connection (NetConnectionEditor *editor,
NMConnection *connection)
{
GSList *pages, *l;
+ NMSettingConnection *sc;
+ const gchar *type;
editor->connection = nm_connection_duplicate (connection);
editor->orig_connection = g_object_ref (connection);
net_connection_editor_update_title (editor);
+ sc = nm_connection_get_setting_connection (connection);
+ type = nm_setting_connection_get_connection_type (sc);
+
add_page (editor, ce_page_details_new (editor->connection, editor->client, editor->settings, editor->device, editor->ap));
- add_page (editor, ce_page_wifi_new (editor->connection, editor->client, editor->settings));
+ if (strcmp (type, NM_SETTING_WIRELESS_SETTING_NAME) == 0)
+ add_page (editor, ce_page_wifi_new (editor->connection, editor->client, editor->settings));
+ else if (strcmp (type, NM_SETTING_WIRED_SETTING_NAME) == 0)
+ add_page (editor, ce_page_ethernet_new (editor->connection, editor->client, editor->settings));
+
add_page (editor, ce_page_ip4_new (editor->connection, editor->client, editor->settings));
add_page (editor, ce_page_ip6_new (editor->connection, editor->client, editor->settings));
- add_page (editor, ce_page_security_new (editor->connection, editor->client, editor->settings));
+
+ if (strcmp (type, NM_SETTING_WIRELESS_SETTING_NAME) == 0)
+ add_page (editor, ce_page_security_new (editor->connection, editor->client, editor->settings));
+ else if (strcmp (type, NM_SETTING_WIRED_SETTING_NAME) == 0)
+ add_page (editor, ce_page_8021x_security_new (editor->connection, editor->client, editor->settings));
+
add_page (editor, ce_page_reset_new (editor->connection, editor->client, editor->settings, editor));
pages = g_slist_copy (editor->initializing_pages);
diff --git a/panels/network/net-device-ethernet.c b/panels/network/net-device-ethernet.c
index 3ac6faa35..f3ef7744d 100644
--- a/panels/network/net-device-ethernet.c
+++ b/panels/network/net-device-ethernet.c
@@ -28,9 +28,14 @@
#include <nm-device.h>
#include <nm-device-ethernet.h>
#include <nm-remote-connection.h>
+#include <nm-utils.h>
#include "panel-common.h"
+#include "egg-list-box/egg-list-box.h"
+#include "connection-editor/net-connection-editor.h"
+#include "connection-editor/ce-page.h"
+
#include "net-device-ethernet.h"
G_DEFINE_TYPE (NetDeviceEthernet, net_device_ethernet, NET_TYPE_DEVICE_SIMPLE)
@@ -51,15 +56,459 @@ device_ethernet_get_speed (NetDeviceSimple *device_simple)
return NULL;
}
+static GSList *
+valid_connections_for_device (NMRemoteSettings *remote_settings,
+ NetDevice *device)
+{
+ GSList *all, *filtered, *iterator, *valid;
+ NMConnection *connection;
+ NMSettingConnection *s_con;
+
+ all = nm_remote_settings_list_connections (remote_settings);
+ filtered = nm_device_filter_connections (net_device_get_nm_device (device), all);
+ g_slist_free (all);
+
+ valid = NULL;
+ for (iterator = filtered; iterator; iterator = iterator->next) {
+ connection = iterator->data;
+ s_con = nm_connection_get_setting_connection (connection);
+ if (!s_con)
+ continue;
+
+ if (nm_setting_connection_get_master (s_con))
+ continue;
+
+ valid = g_slist_prepend (valid, connection);
+ }
+ g_slist_free (filtered);
+
+ return g_slist_reverse (valid);
+}
+
+static GtkWidget *
+device_ethernet_add_to_notebook (NetObject *object,
+ GtkNotebook *notebook,
+ GtkSizeGroup *heading_size_group)
+{
+ NetDeviceEthernet *device = NET_DEVICE_ETHERNET (object);
+ GtkWidget *vbox;
+
+ vbox = GTK_WIDGET (gtk_builder_get_object (device->builder, "vbox6"));
+ g_object_ref (vbox);
+ gtk_container_remove (GTK_CONTAINER (gtk_widget_get_parent (vbox)), vbox);
+ gtk_notebook_append_page (notebook, vbox, NULL);
+ g_object_unref (vbox);
+ return vbox;
+}
+
+static void
+add_details_row (GtkWidget *details, gint top, const gchar *heading, const gchar *value)
+{
+ GtkWidget *label;
+
+ label = gtk_label_new (heading);
+ gtk_style_context_add_class (gtk_widget_get_style_context (label), "dim-label");
+ gtk_widget_set_halign (label, GTK_ALIGN_END);
+ gtk_widget_set_hexpand (label, TRUE);
+ gtk_misc_set_alignment (GTK_MISC (label), 1, 0.5);
+
+ gtk_grid_attach (GTK_GRID (details), label, 0, top, 1, 1);
+
+ label = gtk_label_new (value);
+ gtk_widget_set_halign (label, GTK_ALIGN_START);
+ gtk_widget_set_hexpand (label, TRUE);
+ gtk_misc_set_alignment (GTK_MISC (label), 0, 0.5);
+
+ gtk_grid_attach (GTK_GRID (details), label, 1, top, 1, 1);
+}
+
+static gchar *
+get_last_used_string (NMConnection *connection)
+{
+ gchar *last_used = NULL;
+ GDateTime *now = NULL;
+ GDateTime *then = NULL;
+ gint days;
+ GTimeSpan diff;
+ guint64 timestamp;
+ NMSettingConnection *s_con;
+
+ s_con = nm_connection_get_setting_connection (connection);
+ if (s_con == NULL)
+ goto out;
+ timestamp = nm_setting_connection_get_timestamp (s_con);
+ if (timestamp == 0) {
+ last_used = g_strdup (_("never"));
+ goto out;
+ }
+
+ /* calculate the amount of time that has elapsed */
+ now = g_date_time_new_now_utc ();
+ then = g_date_time_new_from_unix_utc (timestamp);
+ diff = g_date_time_difference (now, then);
+ days = diff / G_TIME_SPAN_DAY;
+ if (days == 0)
+ last_used = g_strdup (_("today"));
+ else if (days == 1)
+ last_used = g_strdup (_("yesterday"));
+ else
+ last_used = g_strdup_printf (ngettext ("%i day ago", "%i days ago", days), days);
+out:
+ if (now != NULL)
+ g_date_time_unref (now);
+ if (then != NULL)
+ g_date_time_unref (then);
+
+ return last_used;
+}
+
+static void
+add_details (GtkWidget *details, NMDevice *device, NMConnection *connection)
+{
+ NMIP4Config *ip4_config = NULL;
+ NMIP6Config *ip6_config = NULL;
+ gchar *ip4_address = NULL;
+ gchar *ip4_route = NULL;
+ gchar *ip4_dns = NULL;
+ gchar *ip6_address = NULL;
+ gint i = 0;
+
+ ip4_config = nm_device_get_ip4_config (device);
+ if (ip4_config) {
+ ip4_address = panel_get_ip4_address_as_string (ip4_config, "address");
+ ip4_route = panel_get_ip4_address_as_string (ip4_config, "gateway");
+ ip4_dns = panel_get_ip4_dns_as_string (ip4_config);
+ }
+ ip6_config = nm_device_get_ip6_config (device);
+ if (ip6_config) {
+ ip6_address = panel_get_ip6_address_as_string (ip6_config);
+ }
+
+ if (ip4_address && ip6_address) {
+ add_details_row (details, i++, _("IP4 Address"), ip4_address);
+ add_details_row (details, i++, _("IP6 Address"), ip6_address);
+ } else if (ip4_address) {
+ add_details_row (details, i++, _("IP Address"), ip4_address);
+ } else if (ip6_address) {
+ add_details_row (details, i++, _("IP Address"), ip6_address);
+ }
+
+ add_details_row (details, i++, _("Hardware Address"),
+ nm_device_ethernet_get_hw_address (NM_DEVICE_ETHERNET (device)));
+
+ if (ip4_route)
+ add_details_row (details, i++, _("Default Route"), ip4_route);
+ if (ip4_dns)
+ add_details_row (details, i++, _("DNS"), ip4_dns);
+
+ if (nm_device_get_state (device) != NM_DEVICE_STATE_ACTIVATED) {
+ gchar *last_used;
+ last_used = get_last_used_string (connection);
+ add_details_row (details, i++, _("Last used"), last_used);
+ g_free (last_used);
+ }
+
+ g_free (ip4_address);
+ g_free (ip4_route);
+ g_free (ip4_dns);
+ g_free (ip6_address);
+}
+
+static void populate_ui (NetDeviceEthernet *device);
+
+static void
+editor_done (NetConnectionEditor *editor,
+ gboolean success,
+ NetDeviceEthernet *device)
+{
+ g_object_unref (editor);
+ populate_ui (device);
+}
+
+static void
+show_details_for_row (GtkButton *button, NetDeviceEthernet *device)
+{
+ GtkWidget *row;
+ NMConnection *connection;
+ GtkWidget *window;
+ NetConnectionEditor *editor;
+ NMClient *client;
+ NMRemoteSettings *settings;
+ NMDevice *nmdev;
+
+ window = gtk_widget_get_toplevel (GTK_WIDGET (button));
+
+ row = GTK_WIDGET (g_object_get_data (G_OBJECT (button), "row"));
+ connection = NM_CONNECTION (g_object_get_data (G_OBJECT (row), "connection"));
+
+ nmdev = net_device_get_nm_device (NET_DEVICE (device));
+ client = net_object_get_client (NET_OBJECT (device));
+ settings = net_object_get_remote_settings (NET_OBJECT (device));
+ editor = net_connection_editor_new (GTK_WINDOW (window), connection, nmdev, NULL, client, settings);
+ g_signal_connect (editor, "done", G_CALLBACK (editor_done), device);
+ net_connection_editor_run (editor);
+}
+
+static void
+add_row (NetDeviceEthernet *device, NMConnection *connection)
+{
+ GtkWidget *row;
+ GtkWidget *widget;
+ GtkWidget *box;
+ GtkWidget *details;
+ NMDevice *nmdev;
+ NMActiveConnection *aconn;
+ gboolean active;
+ GtkWidget *image;
+
+ active = FALSE;
+
+ nmdev = net_device_get_nm_device (NET_DEVICE (device));
+ aconn = nm_device_get_active_connection (nmdev);
+ if (aconn) {
+ const gchar *path1, *path2;
+ path1 = nm_active_connection_get_connection (aconn);
+ path2 = nm_connection_get_path (connection);
+ active = g_strcmp0 (path1, path2) == 0;
+ }
+
+ row = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0);
+ box = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 0);
+ gtk_box_pack_start (GTK_BOX (row), box, FALSE, TRUE, 0);
+ widget = gtk_label_new (nm_connection_get_id (connection));
+ gtk_widget_set_margin_left (widget, 12);
+ gtk_widget_set_margin_right (widget, 12);
+ gtk_widget_set_margin_top (widget, 12);
+ gtk_widget_set_margin_bottom (widget, 12);
+ gtk_box_pack_start (GTK_BOX (box), widget, FALSE, TRUE, 0);
+
+ if (active) {
+ widget = gtk_image_new_from_icon_name ("object-select-symbolic", GTK_ICON_SIZE_MENU);
+ gtk_widget_set_halign (widget, GTK_ALIGN_CENTER);
+ gtk_widget_set_valign (widget, GTK_ALIGN_CENTER);
+ gtk_box_pack_start (GTK_BOX (box), widget, FALSE, TRUE, 0);
+
+ details = gtk_grid_new ();
+ gtk_grid_set_row_spacing (GTK_GRID (details), 10);
+ gtk_grid_set_column_spacing (GTK_GRID (details), 10);
+
+ gtk_box_pack_start (GTK_BOX (row), details, FALSE, TRUE, 0);
+
+ add_details (details, nmdev, connection);
+ }
+
+ /* filler */
+ widget = gtk_label_new ("");
+ gtk_widget_set_hexpand (widget, TRUE);
+ gtk_box_pack_start (GTK_BOX (box), widget, TRUE, TRUE, 0);
+
+ image = gtk_image_new_from_icon_name ("emblem-system-symbolic", GTK_ICON_SIZE_MENU);
+ gtk_widget_show (image);
+ widget = gtk_button_new ();
+ gtk_widget_set_margin_left (widget, 12);
+ gtk_widget_set_margin_right (widget, 12);
+ gtk_widget_set_margin_top (widget, 12);
+ gtk_widget_set_margin_bottom (widget, 12);
+ gtk_widget_show (widget);
+ gtk_container_add (GTK_CONTAINER (widget), image);
+ gtk_widget_set_halign (widget, GTK_ALIGN_CENTER);
+ gtk_widget_set_valign (widget, GTK_ALIGN_CENTER);
+ gtk_box_pack_start (GTK_BOX (box), widget, FALSE, TRUE, 0);
+ g_object_set_data (G_OBJECT (row), "edit", widget);
+ g_object_set_data (G_OBJECT (widget), "row", row);
+ g_signal_connect (widget, "clicked",
+ G_CALLBACK (show_details_for_row), device);
+
+ gtk_widget_show_all (row);
+
+ g_object_set_data (G_OBJECT (row), "connection", connection);
+
+ gtk_container_add (GTK_CONTAINER (device->list), row);
+}
+
+static void
+populate_ui (NetDeviceEthernet *device)
+{
+ NMRemoteSettings *settings;
+ GList *children, *c;
+ GSList *connections, *l;
+ NMConnection *connection;
+ gint n_connections;
+
+ children = gtk_container_get_children (GTK_CONTAINER (device->list));
+ for (c = children; c; c = c->next) {
+ gtk_container_remove (GTK_CONTAINER (device->list), c->data);
+ }
+ g_list_free (children);
+
+ children = gtk_container_get_children (GTK_CONTAINER (device->details));
+ for (c = children; c; c = c->next) {
+ gtk_container_remove (GTK_CONTAINER (device->details), c->data);
+ }
+ g_list_free (children);
+
+ settings = net_object_get_remote_settings (NET_OBJECT (device));
+ connections = valid_connections_for_device (settings, NET_DEVICE (device));
+
+ n_connections = g_slist_length (connections);
+ if (n_connections > 1) {
+ gtk_widget_hide (device->details);
+ gtk_widget_hide (device->details_button);
+ for (l = connections; l; l = l->next) {
+ NMConnection *connection = l->data;
+ add_row (device, connection);
+ }
+ gtk_widget_show (device->scrolled_window);
+ } else if (n_connections == 1) {
+ connection = connections->data;
+ gtk_widget_hide (device->scrolled_window);
+ add_details (device->details, net_device_get_nm_device (NET_DEVICE (device)), connection);
+ gtk_widget_show_all (device->details);
+ gtk_widget_show (device->details_button);
+ g_object_set_data (G_OBJECT (device->details_button), "row", device->details_button);
+ g_object_set_data (G_OBJECT (device->details_button), "connection", connection);
+
+ } else {
+ gtk_widget_hide (device->scrolled_window);
+ gtk_widget_hide (device->details);
+ gtk_widget_hide (device->details_button);
+ }
+}
+
+static void
+remote_settings_read_cb (NMRemoteSettings *settings,
+ NetDeviceEthernet *device)
+{
+ populate_ui (device);
+}
+
+static void
+update_separator (GtkWidget **separator,
+ GtkWidget *child,
+ GtkWidget *before,
+ gpointer user_data)
+{
+ if (before == NULL)
+ return;
+
+ if (*separator == NULL)
+ {
+ *separator = gtk_separator_new (GTK_ORIENTATION_HORIZONTAL);
+ gtk_widget_show (*separator);
+ g_object_ref_sink (*separator);
+ }
+}
+
+static void
+add_profile (GtkButton *button, NetDeviceEthernet *device)
+{
+ NMRemoteSettings *settings;
+ NMConnection *connection;
+ NMSettingConnection *sc;
+ gchar *uuid, *id;
+ NetConnectionEditor *editor;
+ GtkWidget *window;
+ NMClient *client;
+ NMDevice *nmdev;
+ GSList *connections;
+
+ connection = nm_connection_new ();
+ sc = NM_SETTING_CONNECTION (nm_setting_connection_new ());
+ nm_connection_add_setting (connection, NM_SETTING (sc));
+
+ uuid = nm_utils_uuid_generate ();
+
+ settings = net_object_get_remote_settings (NET_OBJECT (device));
+ connections = nm_remote_settings_list_connections (settings);
+ id = ce_page_get_next_available_name (connections, _("Profile %d"));
+ g_slist_free (connections);
+
+ g_object_set (sc,
+ NM_SETTING_CONNECTION_UUID, uuid,
+ NM_SETTING_CONNECTION_ID, id,
+ NM_SETTING_CONNECTION_TYPE, NM_SETTING_WIRED_SETTING_NAME,
+ NM_SETTING_CONNECTION_AUTOCONNECT, TRUE,
+ NULL);
+
+ nm_connection_add_setting (connection, nm_setting_wired_new ());
+
+ g_free (uuid);
+ g_free (id);
+
+ window = gtk_widget_get_toplevel (GTK_WIDGET (button));
+
+ nmdev = net_device_get_nm_device (NET_DEVICE (device));
+ client = net_object_get_client (NET_OBJECT (device));
+ editor = net_connection_editor_new (GTK_WINDOW (window), connection, nmdev, NULL, client, settings);
+ g_signal_connect (editor, "done", G_CALLBACK (editor_done), device);
+ net_connection_editor_run (editor);
+}
+
+static void
+device_ethernet_constructed (GObject *object)
+{
+ NetDeviceEthernet *device = NET_DEVICE_ETHERNET (object);
+ NMRemoteSettings *settings;
+ GtkWidget *list;
+ GtkWidget *swin;
+
+ device->scrolled_window = swin = GTK_WIDGET (gtk_builder_get_object (NET_DEVICE_ETHERNET (object)->builder, "list"));
+ device->list = list = GTK_WIDGET (egg_list_box_new ());
+ egg_list_box_set_selection_mode (EGG_LIST_BOX (list), GTK_SELECTION_NONE);
+ egg_list_box_set_separator_funcs (EGG_LIST_BOX (list), update_separator, NULL, NULL);
+ egg_list_box_add_to_scrolled (EGG_LIST_BOX (list), GTK_SCROLLED_WINDOW (swin));
+ gtk_widget_show (list);
+
+ device->details = GTK_WIDGET (gtk_builder_get_object (NET_DEVICE_ETHERNET (object)->builder, "details"));
+
+ device->details_button = GTK_WIDGET (gtk_builder_get_object (NET_DEVICE_ETHERNET (object)->builder, "details_button"));
+ g_signal_connect (device->details_button, "clicked",
+ G_CALLBACK (show_details_for_row), device);
+
+ device->add_profile_button = GTK_WIDGET (gtk_builder_get_object (NET_DEVICE_ETHERNET (object)->builder, "add_profile_button"));
+ g_signal_connect (device->add_profile_button, "clicked",
+ G_CALLBACK (add_profile), device);
+
+ settings = net_object_get_remote_settings (NET_OBJECT (object));
+ g_signal_connect (settings, "connections-read",
+ G_CALLBACK (remote_settings_read_cb), object);
+}
+
+static void
+device_ethernet_finalize (GObject *object)
+{
+ NetDeviceEthernet *device = NET_DEVICE_ETHERNET (object);
+
+ g_object_unref (device->builder);
+
+ G_OBJECT_CLASS (net_device_ethernet_parent_class)->finalize (object);
+}
+
static void
net_device_ethernet_class_init (NetDeviceEthernetClass *klass)
{
NetDeviceSimpleClass *simple_class = NET_DEVICE_SIMPLE_CLASS (klass);
+ NetObjectClass *obj_class = NET_OBJECT_CLASS (klass);
+ GObjectClass *object_class = G_OBJECT_CLASS (klass);
simple_class->get_speed = device_ethernet_get_speed;
+ obj_class->add_to_notebook = device_ethernet_add_to_notebook;
+ object_class->constructed = device_ethernet_constructed;
+ object_class->finalize = device_ethernet_finalize;
}
static void
-net_device_ethernet_init (NetDeviceEthernet *device_ethernet)
+net_device_ethernet_init (NetDeviceEthernet *device)
{
+ GError *error = NULL;
+
+ device->builder = gtk_builder_new ();
+ gtk_builder_add_from_file (device->builder,
+ GNOMECC_UI_DIR "/network-ethernet.ui",
+ &error);
+ if (error != NULL) {
+ g_warning ("Could not load interface file: %s", error->message);
+ g_error_free (error);
+ return;
+ }
}
diff --git a/panels/network/net-device-ethernet.h b/panels/network/net-device-ethernet.h
index 5c22937b6..d7a2f7ada 100644
--- a/panels/network/net-device-ethernet.h
+++ b/panels/network/net-device-ethernet.h
@@ -41,16 +41,23 @@ typedef struct _NetDeviceEthernetClass NetDeviceEthernetClass;
struct _NetDeviceEthernet
{
- NetDeviceSimple parent;
- NetDeviceEthernetPrivate *priv;
+ NetDeviceSimple parent;
+
+ GtkBuilder *builder;
+
+ GtkWidget *list;
+ GtkWidget *scrolled_window;
+ GtkWidget *details;
+ GtkWidget *details_button;
+ GtkWidget *add_profile_button;
};
struct _NetDeviceEthernetClass
{
- NetDeviceSimpleClass parent_class;
+ NetDeviceSimpleClass parent_class;
};
-GType net_device_ethernet_get_type (void);
+GType net_device_ethernet_get_type (void);
G_END_DECLS
diff --git a/panels/network/network-ethernet.ui b/panels/network/network-ethernet.ui
new file mode 100644
index 000000000..574e84ad2
--- /dev/null
+++ b/panels/network/network-ethernet.ui
@@ -0,0 +1,211 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<interface>
+ <!-- interface-requires gtk+ 3.0 -->
+ <object class="GtkImage" id="image1">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="icon_name">emblem-system-symbolic</property>
+ </object>
+ <object class="GtkWindow" id="window_tmp">
+ <property name="can_focus">False</property>
+ <child>
+ <object class="GtkVBox" id="vbox6">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="border_width">12</property>
+ <property name="spacing">6</property>
+ <child>
+ <object class="GtkGrid" id="grid">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="orientation">vertical</property>
+ <property name="row_spacing">10</property>
+ <property name="column_spacing">6</property>
+ <child>
+ <object class="GtkImage" id="image_device">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="halign">end</property>
+ <property name="valign">start</property>
+ <property name="xalign">1</property>
+ <property name="pixel_size">48</property>
+ <property name="icon_name">network-wired</property>
+ <property name="icon-size">6</property>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkVBox" id="vbox4">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="valign">start</property>
+ <property name="hexpand">True</property>
+ <property name="spacing">3</property>
+ <child>
+ <object class="GtkLabel" id="label_device">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">0</property>
+ <property name="label">Wired</property>
+ <property name="ellipsize">end</property>
+ <attributes>
+ <attribute name="weight" value="bold"/>
+ <attribute name="scale" value="1.2"/>
+ </attributes>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_status">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">0</property>
+ <property name="label">Cable unplugged</property>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">1</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkAlignment" id="alignment_switch">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="halign">end</property>
+ <property name="valign">start</property>
+ <child>
+ <object class="GtkSwitch" id="device_off_switch">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="halign">end</property>
+ <property name="valign">start</property>
+ </object>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">2</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkScrolledWindow" id="list">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="hexpand">True</property>
+ <property name="vexpand">True</property>
+ <property name="hscrollbar_policy">never</property>
+ <property name="shadow_type">in</property>
+ <property name="margin_top">20</property>
+ <child>
+ <placeholder/>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">1</property>
+ <property name="width">3</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkGrid" id="details">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="hexpand">True</property>
+ <property name="vexpand">True</property>
+ <property name="row_spacing">10</property>
+ <property name="column_spacing">10</property>
+ <property name="margin_top">20</property>
+ <child>
+ <placeholder/>
+ </child>
+ <child>
+ <placeholder/>
+ </child>
+ <child>
+ <placeholder/>
+ </child>
+ <child>
+ <placeholder/>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">2</property>
+ <property name="width">3</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="expand">True</property>
+ <property name="fill">True</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkBox" id="actions">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="margin_top">20</property>
+ <child>
+ <object class="GtkButton" id="add_profile_button">
+ <property name="label" translatable="yes">_Add profileā€¦</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">True</property>
+ <property name="halign">start</property>
+ <property name="use_underline">True</property>
+ </object>
+ <packing>
+ <property name="expand">True</property>
+ <property name="fill">True</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkButton" id="details_button">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">True</property>
+ <property name="halign">end</property>
+ <property name="image">image1</property>
+ </object>
+ <packing>
+ <property name="expand">True</property>
+ <property name="fill">True</property>
+ <property name="position">1</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">True</property>
+ <property name="position">1</property>
+ </packing>
+ </child>
+ </object>
+ </child>
+ </object>
+ <object class="GtkSizeGroup" id="sizegroup1"/>
+</interface>
diff --git a/panels/network/network-simple.ui b/panels/network/network-simple.ui
index a5ceb47a9..194e25f60 100644
--- a/panels/network/network-simple.ui
+++ b/panels/network/network-simple.ui
@@ -1,6 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
<!-- interface-requires gtk+ 3.0 -->
+ <object class="GtkOffscreenWindow" id="offscreenwindow1">
+ <property name="can_focus">False</property>
+ <child>
+ <placeholder/>
+ </child>
+ </object>
<object class="GtkWindow" id="window_tmp">
<property name="can_focus">False</property>
<child>
@@ -82,174 +88,6 @@
</packing>
</child>
<child>
- <object class="GtkLabel" id="heading_mac">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="xalign">1</property>
- <property name="label" translatable="yes">Hardware Address</property>
- <property name="mnemonic_widget">label_mac</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="heading_ipv4">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="xalign">1</property>
- <property name="label" translatable="yes">IPv4 Address</property>
- <property name="mnemonic_widget">label_ipv4</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">3</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="heading_ipv6">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="xalign">1</property>
- <property name="label" translatable="yes">IPv6 Address</property>
- <property name="mnemonic_widget">label_ipv6</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">4</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="heading_route">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="xalign">1</property>
- <property name="label" translatable="yes">Default Route</property>
- <property name="mnemonic_widget">label_route</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">5</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="heading_dns">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="xalign">1</property>
- <property name="yalign">0</property>
- <property name="label" translatable="yes">DNS</property>
- <property name="mnemonic_widget">label_dns</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">6</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="label_mac">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="xalign">0</property>
- <property name="label">AA:BB:CC:DD:55:66:77:88</property>
- <property name="selectable">True</property>
- </object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">1</property>
- <property name="width">2</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="label_ipv4">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="xalign">0</property>
- <property name="label">127.0.0.1</property>
- <property name="selectable">True</property>
- </object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">3</property>
- <property name="width">2</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="label_ipv6">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="xalign">0</property>
- <property name="label">::1</property>
- <property name="selectable">True</property>
- </object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">4</property>
- <property name="width">2</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="label_route">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="xalign">0</property>
- <property name="label">127.0.0.1</property>
- <property name="selectable">True</property>
- </object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">5</property>
- <property name="width">2</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="label_dns">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="xalign">0</property>
- <property name="yalign">0</property>
- <property name="label">127.0.0.1</property>
- <property name="wrap">True</property>
- <property name="selectable">True</property>
- </object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">6</property>
- <property name="width">2</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
<object class="GtkAlignment" id="alignment_switch">
<property name="visible">True</property>
<property name="can_focus">False</property>
@@ -272,13 +110,189 @@
</packing>
</child>
<child>
- <placeholder/>
- </child>
- <child>
- <placeholder/>
- </child>
- <child>
- <placeholder/>
+ <object class="GtkGrid" id="grid1">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="margin_top">20</property>
+ <property name="row_spacing">10</property>
+ <property name="column_spacing">6</property>
+ <property name="row_homogeneous">True</property>
+ <property name="column_homogeneous">True</property>
+ <child>
+ <object class="GtkLabel" id="heading_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">Hardware Address</property>
+ <property name="mnemonic_widget">label_mac</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_ipv4">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">IPv4 Address</property>
+ <property name="mnemonic_widget">label_ipv4</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">1</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_ipv6">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">IPv6 Address</property>
+ <property name="mnemonic_widget">label_ipv6</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">2</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_route">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="label" translatable="yes">Default Route</property>
+ <property name="mnemonic_widget">label_route</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">3</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="heading_dns">
+ <property name="visible">True</property>
+ <property name="can_focus">False</property>
+ <property name="xalign">1</property>
+ <property name="yalign">0</property>
+ <property name="label" translatable="yes">DNS</property>
+ <property name="mnemonic_widget">label_dns</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">4</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_mac">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="xalign">0</property>
+ <property name="label">AA:BB:CC:DD:55:66:77:88</property>
+ <property name="selectable">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">0</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_ipv4">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="xalign">0</property>
+ <property name="label">127.0.0.1</property>
+ <property name="selectable">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">1</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_ipv6">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="xalign">0</property>
+ <property name="label">::1</property>
+ <property name="selectable">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">2</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_route">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="xalign">0</property>
+ <property name="label">127.0.0.1</property>
+ <property name="selectable">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">3</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="label_dns">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="xalign">0</property>
+ <property name="yalign">0</property>
+ <property name="label">127.0.0.1</property>
+ <property name="wrap">True</property>
+ <property name="selectable">True</property>
+ </object>
+ <packing>
+ <property name="left_attach">1</property>
+ <property name="top_attach">4</property>
+ <property name="width">1</property>
+ <property name="height">1</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="left_attach">0</property>
+ <property name="top_attach">1</property>
+ <property name="width">3</property>
+ <property name="height">1</property>
+ </packing>
</child>
</object>
<packing>
@@ -321,13 +335,5 @@
</object>
</child>
</object>
- <object class="GtkSizeGroup" id="sizegroup1">
- <widgets>
- <widget name="heading_mac"/>
- <widget name="heading_ipv4"/>
- <widget name="heading_ipv6"/>
- <widget name="heading_route"/>
- <widget name="heading_dns"/>
- </widgets>
- </object>
+ <object class="GtkSizeGroup" id="sizegroup1"/>
</interface>
diff --git a/panels/network/panel-common.c b/panels/network/panel-common.c
index fe7baf4eb..cafdc327b 100644
--- a/panels/network/panel-common.c
+++ b/panels/network/panel-common.c
@@ -655,3 +655,21 @@ panel_unset_device_widgets (GtkBuilder *builder)
panel_set_device_widget_details (builder, "dns", NULL);
panel_set_device_widget_details (builder, "route", NULL);
}
+
+gchar *
+panel_get_ip4_address_as_string (NMIP4Config *ip4, const gchar *what)
+{
+ return get_ipv4_config_address_as_string (ip4, what);
+}
+
+gchar *
+panel_get_ip4_dns_as_string (NMIP4Config *ip4)
+{
+ return get_ipv4_config_name_servers_as_string (ip4);
+}
+
+gchar *
+panel_get_ip6_address_as_string (NMIP6Config *ip6)
+{
+ return get_ipv6_config_address_as_string (ip6);
+}
diff --git a/panels/network/panel-common.h b/panels/network/panel-common.h
index c55d46b3a..9288e4fbe 100644
--- a/panels/network/panel-common.h
+++ b/panels/network/panel-common.h
@@ -45,6 +45,9 @@ gboolean panel_set_device_widget_header (GtkBuilder *buil
void panel_set_device_widgets (GtkBuilder *builder,
NMDevice *device);
void panel_unset_device_widgets (GtkBuilder *builder);
+gchar *panel_get_ip4_address_as_string (NMIP4Config *config, const gchar *what);
+gchar *panel_get_ip4_dns_as_string (NMIP4Config *config);
+gchar *panel_get_ip6_address_as_string (NMIP6Config *config);
G_END_DECLS