diff --git a/panels/network/cc-network-panel.c b/panels/network/cc-network-panel.c index f74e2bdf2..0579fcc0b 100644 --- a/panels/network/cc-network-panel.c +++ b/panels/network/cc-network-panel.c @@ -1299,34 +1299,6 @@ device_off_toggled (GtkSwitch *sw, active = gtk_switch_get_active (sw); object = get_selected_object (panel); - if (NET_IS_VPN (object)) { - - NMConnection *connection; - - connection = net_vpn_get_connection (NET_VPN (object)); - if (active) - nm_client_activate_connection (panel->priv->client, - connection, NULL, NULL, - NULL, NULL); - else { - const gchar *path; - NMActiveConnection *a; - const GPtrArray *acs; - gint i; - - path = nm_connection_get_path (connection); - - acs = nm_client_get_active_connections (panel->priv->client); - for (i = 0; i < acs->len; i++) { - a = (NMActiveConnection*)acs->pdata[i]; - if (strcmp (nm_active_connection_get_connection (a), path) == 0) { - nm_client_deactivate_connection (panel->priv->client, a); - break; - } - } - } - } - if (NET_IS_DEVICE (object)) { device = net_device_get_nm_device (NET_DEVICE (object)); switch (nm_device_get_device_type (device)) { @@ -2096,121 +2068,6 @@ nm_device_refresh_device_ui (CcNetworkPanel *panel, NetDevice *device) out: ; } -static void -nm_device_refresh_vpn_ui (CcNetworkPanel *panel, NetVpn *vpn) -{ - GtkWidget *widget; - GtkWidget *sw; - const gchar *sub_pane = "vpn"; - const gchar *status; - CcNetworkPanelPrivate *priv = panel->priv; - const GPtrArray *acs; - NMActiveConnection *a; - gint i; - const gchar *path; - const gchar *apath; - NMVPNConnectionState state; - gchar *title; - GtkListStore *liststore_devices; - GtkTreeIter iter; - - sw = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "device_vpn_off_switch")); - gtk_widget_set_visible (sw, TRUE); - - widget = GTK_WIDGET (gtk_builder_get_object (panel->priv->builder, - "button_vpn_options")); - gtk_widget_set_visible (widget, TRUE); - gtk_widget_set_sensitive (widget, TRUE); - - /* use proxy note page */ - widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "notebook_types")); - gtk_notebook_set_current_page (GTK_NOTEBOOK (widget), 3); - - /* set VPN icon */ - widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "image_vpn_device")); - gtk_image_set_from_icon_name (GTK_IMAGE (widget), - "network-vpn", - GTK_ICON_SIZE_DIALOG); - - /* update title */ - widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "label_vpn_device")); - title = g_strdup_printf (_("%s VPN"), nm_connection_get_id (net_vpn_get_connection (vpn))); - net_object_set_title (NET_OBJECT (vpn), title); - gtk_label_set_label (GTK_LABEL (widget), title); - - /* update list store title */ - liststore_devices = GTK_LIST_STORE (gtk_builder_get_object (panel->priv->builder, - "liststore_devices")); - if (find_model_iter_by_object (GTK_TREE_MODEL (liststore_devices), NET_OBJECT (vpn), &iter)) { - gtk_list_store_set (liststore_devices, - &iter, - PANEL_DEVICES_COLUMN_TITLE, title, - -1); - } - g_free (title); - - /* use status */ - state = net_vpn_get_state (vpn); - - acs = nm_client_get_active_connections (priv->client); - if (acs != NULL) { - path = nm_connection_get_path (net_vpn_get_connection (vpn)); - for (i = 0; i < acs->len; i++) { - a = (NMActiveConnection*)acs->pdata[i]; - - apath = nm_active_connection_get_connection (a); - if (NM_IS_VPN_CONNECTION (a) && strcmp (apath, path) == 0) { - state = nm_vpn_connection_get_vpn_state (NM_VPN_CONNECTION (a)); - break; - } - } - } - - widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "label_vpn_status")); - status = panel_vpn_state_to_localized_string (state); - gtk_label_set_label (GTK_LABEL (widget), status); - priv->updating_device = TRUE; - gtk_switch_set_active (GTK_SWITCH (sw), - state != NM_VPN_CONNECTION_STATE_FAILED && - state != NM_VPN_CONNECTION_STATE_DISCONNECTED); - priv->updating_device = FALSE; - - /* service type */ - panel_set_widget_data (panel, - sub_pane, - "service_type", - net_vpn_get_service_type (vpn)); - - /* gateway */ - panel_set_widget_data (panel, - sub_pane, - "gateway", - net_vpn_get_gateway (vpn)); - - /* groupname */ - panel_set_widget_data (panel, - sub_pane, - "group_name", - net_vpn_get_id (vpn)); - - /* username */ - panel_set_widget_data (panel, - sub_pane, - "username", - net_vpn_get_username (vpn)); - - /* password */ - panel_set_widget_data (panel, - sub_pane, - "group_password", - net_vpn_get_password (vpn)); -} - static void panel_set_notebook_page_for_object (CcNetworkPanel *panel, NetObject *object) { @@ -2272,18 +2129,6 @@ refresh_ui_idle (gpointer data) /* do we have a new-style NetObject-style panel widget */ panel_set_notebook_page_for_object (panel, object); - /* VPN */ - if (NET_IS_VPN (object)) { - - nm_device_refresh_vpn_ui (panel, NET_VPN (object)); - - /* we're able to remove the VPN connection */ - widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, - "remove_toolbutton")); - gtk_widget_set_sensitive (widget, TRUE); - goto out; - } - /* device */ if (NET_IS_DEVICE (object)) { @@ -2323,7 +2168,6 @@ panel_add_proxy_device (CcNetworkPanel *panel) GtkListStore *liststore_devices; GtkTreeIter iter; NetProxy *proxy; - GtkWidget *widget; GtkNotebook *notebook; GtkSizeGroup *size_group; @@ -2519,6 +2363,8 @@ panel_add_vpn_device (CcNetworkPanel *panel, NMConnection *connection) GtkTreeIter iter; NetVpn *net_vpn; const gchar *id; + GtkNotebook *notebook; + GtkSizeGroup *size_group; /* does already exist */ id = nm_connection_get_path (connection); @@ -2528,9 +2374,19 @@ panel_add_vpn_device (CcNetworkPanel *panel, NMConnection *connection) /* add as a virtual object */ net_vpn = net_vpn_new (); net_vpn_set_connection (net_vpn, connection); + net_object_set_client (NET_OBJECT (net_vpn), panel->priv->client); net_object_set_id (NET_OBJECT (net_vpn), id); register_object_interest (panel, NET_OBJECT (net_vpn)); + /* add as a panel */ + notebook = GTK_NOTEBOOK (gtk_builder_get_object (panel->priv->builder, + "notebook_types")); + size_group = GTK_SIZE_GROUP (gtk_builder_get_object (panel->priv->builder, + "sizegroup1")); + net_object_add_to_notebook (NET_OBJECT (net_vpn), + notebook, + size_group); + liststore_devices = GTK_LIST_STORE (gtk_builder_get_object (panel->priv->builder, "liststore_devices")); title = g_strdup_printf (_("%s VPN"), nm_connection_get_id (connection)); @@ -2663,9 +2519,6 @@ edit_connection (GtkButton *button, CcNetworkPanel *panel) object = get_selected_object (panel); if (object == NULL) return; - else if (NET_IS_VPN (object)) { - c = net_vpn_get_connection (NET_VPN (object)); - } else { device = net_device_get_nm_device (NET_DEVICE (object)); c = find_connection_for_device (panel, device); @@ -2827,19 +2680,14 @@ static void remove_connection (GtkToolButton *button, CcNetworkPanel *panel) { NetObject *object; - NMConnection *connection; /* get current device */ object = get_selected_object (panel); if (object == NULL) return; - /* VPN */ - if (NET_IS_VPN (object)) { - connection = net_vpn_get_connection (NET_VPN (object)); - nm_remote_connection_delete (NM_REMOTE_CONNECTION (connection), NULL, panel); - return; - } + /* delete the object */ + net_object_delete (object); } static void @@ -3659,10 +3507,6 @@ cc_network_panel_init (CcNetworkPanel *panel) "device_mobilebb_off_switch")); g_signal_connect (widget, "notify::active", G_CALLBACK (device_off_toggled), panel); - widget = GTK_WIDGET (gtk_builder_get_object (panel->priv->builder, - "device_vpn_off_switch")); - g_signal_connect (widget, "notify::active", - G_CALLBACK (device_off_toggled), panel); g_signal_connect (panel->priv->client, "notify::wireless-enabled", G_CALLBACK (wireless_enabled_toggled), panel); @@ -3695,11 +3539,6 @@ cc_network_panel_init (CcNetworkPanel *panel) g_signal_connect (widget, "clicked", G_CALLBACK (edit_connection), panel); - widget = GTK_WIDGET (gtk_builder_get_object (panel->priv->builder, - "button_vpn_options")); - g_signal_connect (widget, "clicked", - G_CALLBACK (edit_connection), panel); - widget = GTK_WIDGET (gtk_builder_get_object (panel->priv->builder, "add_toolbutton")); g_signal_connect (widget, "clicked", diff --git a/panels/network/net-vpn.c b/panels/network/net-vpn.c index 5b27de1c8..aefe4f50d 100644 --- a/panels/network/net-vpn.c +++ b/panels/network/net-vpn.c @@ -1,6 +1,6 @@ /* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*- * - * Copyright (C) 2011 Richard Hughes + * Copyright (C) 2011-2012 Richard Hughes * * Licensed under the GNU General Public License Version 2 * @@ -24,17 +24,22 @@ #include #include +#include "panel-common.h" + #include "net-vpn.h" -#include "nm-setting-vpn.h" +#include "nm-client.h" #include "nm-remote-connection.h" +#include "nm-setting-vpn.h" #define NET_VPN_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), NET_TYPE_VPN, NetVpnPrivate)) struct _NetVpnPrivate { + GtkBuilder *builder; NMConnection *connection; gchar *service_type; gboolean valid; + gboolean updating_device; }; G_DEFINE_TYPE (NetVpn, net_vpn, NET_TYPE_OBJECT) @@ -106,19 +111,7 @@ net_vpn_set_connection (NetVpn *vpn, NMConnection *connection) priv->service_type = net_vpn_connection_to_type (priv->connection); } -NMConnection * -net_vpn_get_connection (NetVpn *vpn) -{ - return vpn->priv->connection; -} - -const gchar * -net_vpn_get_service_type (NetVpn *vpn) -{ - return vpn->priv->service_type; -} - -NMVPNConnectionState +static NMVPNConnectionState net_vpn_get_state (NetVpn *vpn) { NetVpnPrivate *priv = vpn->priv; @@ -179,7 +172,7 @@ get_vpn_key_group_password (const char *vpn_type) return ""; } -const gchar * +static const gchar * net_vpn_get_gateway (NetVpn *vpn) { NetVpnPrivate *priv = vpn->priv; @@ -189,7 +182,7 @@ net_vpn_get_gateway (NetVpn *vpn) return nm_setting_vpn_get_data_item (nm_connection_get_setting_vpn (priv->connection), key); } -const gchar * +static const gchar * net_vpn_get_id (NetVpn *vpn) { NetVpnPrivate *priv = vpn->priv; @@ -199,7 +192,7 @@ net_vpn_get_id (NetVpn *vpn) return nm_setting_vpn_get_data_item (nm_connection_get_setting_vpn (priv->connection), key); } -const gchar * +static const gchar * net_vpn_get_username (NetVpn *vpn) { NetVpnPrivate *priv = vpn->priv; @@ -209,7 +202,7 @@ net_vpn_get_username (NetVpn *vpn) return nm_setting_vpn_get_data_item (nm_connection_get_setting_vpn (priv->connection), key); } -const gchar * +static const gchar * net_vpn_get_password (NetVpn *vpn) { NetVpnPrivate *priv = vpn->priv; @@ -219,6 +212,215 @@ net_vpn_get_password (NetVpn *vpn) return nm_setting_vpn_get_data_item (nm_connection_get_setting_vpn (priv->connection), key); } +static void +vpn_proxy_delete (NetObject *object) +{ + NetVpn *vpn = NET_VPN (object); + nm_remote_connection_delete (NM_REMOTE_CONNECTION (vpn->priv->connection), + NULL, vpn); +} + +static GtkWidget * +vpn_proxy_add_to_notebook (NetObject *object, + GtkNotebook *notebook, + GtkSizeGroup *heading_size_group) +{ + GtkWidget *widget; + GtkWindow *window; + NetVpn *vpn = NET_VPN (object); + + /* add widgets to size group */ + widget = GTK_WIDGET (gtk_builder_get_object (vpn->priv->builder, + "heading_vpn_group_password")); + gtk_size_group_add_widget (heading_size_group, widget); + + /* reparent */ + window = GTK_WINDOW (gtk_builder_get_object (vpn->priv->builder, + "window_tmp")); + widget = GTK_WIDGET (gtk_builder_get_object (vpn->priv->builder, + "vbox9")); + g_object_ref (widget); + gtk_container_remove (GTK_CONTAINER (window), widget); + gtk_notebook_append_page (notebook, widget, NULL); + g_object_unref (widget); + return widget; +} + +static void +panel_set_widget_data (NetVpn *vpn, + const gchar *widget_suffix, + const gchar *value) +{ + gchar *heading_id; + gchar *label_id = NULL; + GtkWidget *heading; + GtkWidget *widget; + const gchar *sub_pane = "vpn"; + NetVpnPrivate *priv = vpn->priv; + + /* hide the row if there is no value */ + heading_id = g_strdup_printf ("heading_%s_%s", sub_pane, widget_suffix); + label_id = g_strdup_printf ("label_%s_%s", sub_pane, widget_suffix); + heading = GTK_WIDGET (gtk_builder_get_object (priv->builder, heading_id)); + widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, label_id)); + if (heading == NULL || widget == NULL) { + g_critical ("no widgets %s, %s found", heading_id, label_id); + return; + } + g_free (heading_id); + g_free (label_id); + + if (value == NULL) { + gtk_widget_hide (heading); + gtk_widget_hide (widget); + } else { + /* there exists a value */ + gtk_widget_show (heading); + gtk_widget_show (widget); + gtk_label_set_label (GTK_LABEL (widget), value); + } +} + +static void +nm_device_refresh_vpn_ui (NetVpn *vpn) +{ + GtkWidget *widget; + GtkWidget *sw; + const gchar *status; + NetVpnPrivate *priv = vpn->priv; + const GPtrArray *acs; + NMActiveConnection *a; + gint i; + const gchar *path; + const gchar *apath; + NMVPNConnectionState state; + gchar *title; + NMClient *client; + + sw = GTK_WIDGET (gtk_builder_get_object (priv->builder, + "device_vpn_off_switch")); + gtk_widget_set_visible (sw, TRUE); + + /* set VPN icon */ + widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, + "image_vpn_device")); + gtk_image_set_from_icon_name (GTK_IMAGE (widget), + "network-vpn", + GTK_ICON_SIZE_DIALOG); + + /* update title */ + widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, + "label_vpn_device")); + title = g_strdup_printf (_("%s VPN"), nm_connection_get_id (vpn->priv->connection)); + net_object_set_title (NET_OBJECT (vpn), title); + gtk_label_set_label (GTK_LABEL (widget), title); + g_free (title); + + /* use status */ + state = net_vpn_get_state (vpn); + client = net_object_get_client (NET_OBJECT (vpn)); + acs = nm_client_get_active_connections (client); + if (acs != NULL) { + path = nm_connection_get_path (vpn->priv->connection); + for (i = 0; i < acs->len; i++) { + a = (NMActiveConnection*)acs->pdata[i]; + + apath = nm_active_connection_get_connection (a); + if (NM_IS_VPN_CONNECTION (a) && strcmp (apath, path) == 0) { + state = nm_vpn_connection_get_vpn_state (NM_VPN_CONNECTION (a)); + break; + } + } + } + + widget = GTK_WIDGET (gtk_builder_get_object (priv->builder, + "label_vpn_status")); + status = panel_vpn_state_to_localized_string (state); + gtk_label_set_label (GTK_LABEL (widget), status); + priv->updating_device = TRUE; + gtk_switch_set_active (GTK_SWITCH (sw), + state != NM_VPN_CONNECTION_STATE_FAILED && + state != NM_VPN_CONNECTION_STATE_DISCONNECTED); + priv->updating_device = FALSE; + + /* service type */ + panel_set_widget_data (vpn, + "service_type", + vpn->priv->service_type); + + /* gateway */ + panel_set_widget_data (vpn, + "gateway", + net_vpn_get_gateway (vpn)); + + /* groupname */ + panel_set_widget_data (vpn, + "group_name", + net_vpn_get_id (vpn)); + + /* username */ + panel_set_widget_data (vpn, + "username", + net_vpn_get_username (vpn)); + + /* password */ + panel_set_widget_data (vpn, + "group_password", + net_vpn_get_password (vpn)); +} + +static void +device_off_toggled (GtkSwitch *sw, + GParamSpec *pspec, + NetVpn *vpn) +{ + const gchar *path; + const GPtrArray *acs; + gboolean active; + gint i; + NMActiveConnection *a; + NMClient *client; + + if (vpn->priv->updating_device) + return; + + active = gtk_switch_get_active (sw); + if (active) { + client = net_object_get_client (NET_OBJECT (vpn)); + nm_client_activate_connection (client, + vpn->priv->connection, NULL, NULL, + NULL, NULL); + } else { + path = nm_connection_get_path (vpn->priv->connection); + client = net_object_get_client (NET_OBJECT (vpn)); + acs = nm_client_get_active_connections (client); + for (i = 0; i < acs->len; i++) { + a = (NMActiveConnection*)acs->pdata[i]; + if (strcmp (nm_active_connection_get_connection (a), path) == 0) { + nm_client_deactivate_connection (client, a); + break; + } + } + } +} + +static void +edit_connection (GtkButton *button, NetVpn *vpn) +{ + const gchar *uuid; + gchar *cmdline; + GError *error = NULL; + + uuid = nm_connection_get_uuid (vpn->priv->connection); + cmdline = g_strdup_printf ("nm-connection-editor --edit %s", uuid); + g_debug ("Launching '%s'\n", cmdline); + if (!g_spawn_command_line_async (cmdline, &error)) { + g_warning ("Failed to launch nm-connection-editor: %s", error->message); + g_error_free (error); + } + g_free (cmdline); +} + static void net_vpn_finalize (GObject *object) { @@ -235,21 +437,52 @@ static void net_vpn_class_init (NetVpnClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS (klass); + NetObjectClass *parent_class = NET_OBJECT_CLASS (klass); + object_class->finalize = net_vpn_finalize; + parent_class->add_to_notebook = vpn_proxy_add_to_notebook; + parent_class->delete = vpn_proxy_delete; g_type_class_add_private (klass, sizeof (NetVpnPrivate)); } static void net_vpn_init (NetVpn *vpn) { + GError *error = NULL; + GtkWidget *widget; + vpn->priv = NET_VPN_GET_PRIVATE (vpn); + + vpn->priv->builder = gtk_builder_new (); + gtk_builder_add_from_file (vpn->priv->builder, + GNOMECC_UI_DIR "/network-vpn.ui", + &error); + if (error != NULL) { + g_warning ("Could not load interface file: %s", error->message); + g_error_free (error); + return; + } + + widget = GTK_WIDGET (gtk_builder_get_object (vpn->priv->builder, + "device_vpn_off_switch")); + g_signal_connect (widget, "notify::active", + G_CALLBACK (device_off_toggled), vpn); + + widget = GTK_WIDGET (gtk_builder_get_object (vpn->priv->builder, + "button_vpn_options")); + g_signal_connect (widget, "clicked", + G_CALLBACK (edit_connection), vpn); + + nm_device_refresh_vpn_ui (vpn); } NetVpn * net_vpn_new (void) { NetVpn *vpn; - vpn = g_object_new (NET_TYPE_VPN, NULL); + vpn = g_object_new (NET_TYPE_VPN, + "removable", TRUE, + NULL); return NET_VPN (vpn); } diff --git a/panels/network/net-vpn.h b/panels/network/net-vpn.h index da79d2fc9..f11fcf6b5 100644 --- a/panels/network/net-vpn.h +++ b/panels/network/net-vpn.h @@ -57,13 +57,6 @@ GType net_vpn_get_type (void); NetVpn *net_vpn_new (void); void net_vpn_set_connection (NetVpn *vpn, NMConnection *connection); -NMConnection *net_vpn_get_connection (NetVpn *vpn); -const gchar *net_vpn_get_service_type (NetVpn *vpn); -const gchar *net_vpn_get_gateway (NetVpn *vpn); -const gchar *net_vpn_get_id (NetVpn *vpn); -const gchar *net_vpn_get_username (NetVpn *vpn); -const gchar *net_vpn_get_password (NetVpn *vpn); -NMVPNConnectionState net_vpn_get_state (NetVpn *vpn); G_END_DECLS diff --git a/panels/network/network-vpn.ui b/panels/network/network-vpn.ui new file mode 100644 index 000000000..de1e4a069 --- /dev/null +++ b/panels/network/network-vpn.ui @@ -0,0 +1,336 @@ + + + + + + + + + + + + + VPN + vpn + + + + + False + + + True + False + 12 + 6 + + + True + False + start + 10 + 6 + + + True + False + end + start + 1 + 48 + network-vpn + 6 + + + 0 + 0 + 1 + 1 + + + + + True + False + start + True + 3 + + + True + False + 0 + VPN + end + + + + + + + False + False + 0 + + + + + True + False + 0 + Not connected + + + False + False + 1 + + + + + 1 + 0 + 1 + 1 + + + + + True + False + 1 + VPN Type + label_vpn_service_type + + + + 0 + 1 + 1 + 1 + + + + + True + False + 1 + Gateway + label_vpn_gateway + + + + 0 + 2 + 1 + 1 + + + + + True + False + 1 + Group Name + label_vpn_group_name + + + + 0 + 3 + 1 + 1 + + + + + True + False + 1 + Group Password + label_vpn_group_password + + + + 0 + 4 + 1 + 1 + + + + + True + False + 1 + Username + label_vpn_username + + + + 0 + 5 + 1 + 1 + + + + + True + False + 0 + openvpn + True + + + 1 + 1 + 2 + 1 + + + + + True + False + 0 + AA:BB:CC:DD:55:66:77:88 + True + + + 1 + 2 + 2 + 1 + + + + + True + False + 0 + SEKRIT + True + + + 1 + 3 + 2 + 1 + + + + + True + False + 0 + ********** + True + + + 1 + 4 + 2 + 1 + + + + + True + False + 0 + smithy + True + + + 1 + 5 + 2 + 1 + + + + + True + False + end + start + + + False + True + True + end + start + + + + + 2 + 0 + 1 + 1 + + + + + True + True + 0 + + + + + True + False + + + _Configure... + False + True + True + True + end + end + True + True + True + 1 + + + False + True + end + 0 + + + + + True + True + 1 + + + + + + + + + + + + + + + diff --git a/panels/network/network.ui b/panels/network/network.ui index 60f23b5b2..068da5d03 100644 --- a/panels/network/network.ui +++ b/panels/network/network.ui @@ -1605,319 +1605,6 @@ - - True - False - 12 - 6 - - - True - False - start - 10 - 6 - - - True - False - end - start - 1 - 48 - network-vpn - 6 - - - 0 - 0 - 1 - 1 - - - - - True - False - start - True - 3 - - - True - False - 0 - VPN - end - - - - - - - False - False - 0 - - - - - True - False - 0 - Not connected - - - False - False - 1 - - - - - 1 - 0 - 1 - 1 - - - - - True - False - 1 - VPN Type - label_vpn_service_type - - - - 0 - 1 - 1 - 1 - - - - - True - False - 1 - Gateway - label_vpn_gateway - - - - 0 - 2 - 1 - 1 - - - - - True - False - 1 - Group Name - label_vpn_group_name - - - - 0 - 3 - 1 - 1 - - - - - True - False - 1 - Group Password - label_vpn_group_password - - - - 0 - 4 - 1 - 1 - - - - - True - False - 1 - Username - label_vpn_username - - - - 0 - 5 - 1 - 1 - - - - - True - False - 0 - openvpn - True - - - 1 - 1 - 2 - 1 - - - - - True - False - 0 - AA:BB:CC:DD:55:66:77:88 - True - - - 1 - 2 - 2 - 1 - - - - - True - False - 0 - SEKRIT - True - - - 1 - 3 - 2 - 1 - - - - - True - False - 0 - ********** - True - - - 1 - 4 - 2 - 1 - - - - - True - False - 0 - smithy - True - - - 1 - 5 - 2 - 1 - - - - - True - False - end - start - - - False - True - True - end - start - False - - - Disable VPN - - - - - - - 2 - 0 - 1 - 1 - - - - - True - True - 0 - - - - - True - False - - - _Configure... - False - True - True - True - True - 1 - end - end - True - True - - - False - True - end - 0 - - - - - True - True - 1 - - - - - 2 -