--- /dev/null
+/*
+ * This file is part of vpngui
+ *
+ * Copyright © 2009 Nokia Corporation and/or its subsidiary(-ies)
+ *
+ * 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ * */
+
+#define SCRATCHBOX 0
+
+#define DBUS_API_SUBJECT_TO_CHANGE
+#include <sys/ioctl.h>
+#include <sys/socket.h>
+#include <net/if.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+#include <dbus/dbus-glib.h>
+#include <dbus/dbus-glib-bindings.h>
+#include <dbus/dbus.h>
+
+#include <glib.h>
+#include <glib-object.h>
+
+#include <conicevent.h>
+#include <coniciap.h>
+#include <conicconnection.h>
+#include <conicconnectionevent.h>
+
+#include <libhildondesktop/libhildondesktop.h>
+#include <hildon/hildon-dialog.h>
+#include <hildon/hildon-caption.h>
+#include <hildon/hildon-check-button.h>
+#include <hildon/hildon-pannable-area.h>
+#include <hildon/hildon-banner.h>
+#include <hildon/hildon-number-editor.h>
+#include <hildon/hildon-entry.h>
+#include <sys/types.h>
+#include <gtk/gtk.h>
+#include <gconf/gconf.h>
+#include <gconf/gconf-client.h>
+#include <stdio.h>
+#include <string.h>
+
+/* for temporary stuff like getenv() and sleep() */
+#include <unistd.h>
+#include "config.h"
+#include "vpncfg.h"
+
+#include <stdlib.h>
+#include <libosso.h>
+#include <hildon/hildon-button.h>
+#include <hildon/hildon-note.h>
+
+#include "macros.h"
+#include "vpngui.h"
+
+#define STATUS_MENU_VPNGUI_ICON "general_synchronization"
+#define STATUS_MENU_VPNGUI_ICON_SIZE 48
+#define STATUS_AREA_VPNGUI_ICON_SIZE 16
+
+#define VPNC_DBUS_LISTENER_TYPE "type='signal',interface='org.maemo.vpnc'"
+#define VPNC_DBUS_LISTENER_SERVICE "org.maemo.vpnc"
+#define VPNC_DBUS_LISTENER_SIGNAL "dBusSignal"
+
+#define DEBUG
+
+#ifdef DEBUG
+# define TRACE(fmtstr, args...) \
+ printf("\033[1;32VPNGUI_PLUGIN\033[0;39m: %s: " fmtstr "\n", \
+ __func__, ##args); \
+ fflush (stdout)
+#else
+# define TRACE(fmtstr, args...) {}
+#endif
+static gchar *iface_addr(const gchar *iface);
+static gboolean do_disconnect(PluginInfo *self, const gboolean forced);
+static void vpngui_destroy(GObject *object);
+void error_msg(const char *format, ...)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ GtkWidget* dialog;
+ gchar *string;
+ va_list args;
+ va_start(args, format);
+ string = g_strdup_vprintf(format, args);
+ dialog = hildon_note_new_information_with_icon_name(NULL, string,
+ GTK_STOCK_DIALOG_ERROR);
+ gtk_dialog_run(GTK_DIALOG(dialog));
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+ g_free(string);
+ va_end(args);
+}
+
+struct VpnGuiListData{
+ GtkWidget *radio_button;
+ int ap_no;
+ char* vpn_name;
+};
+struct VpnGuiListData *vpn_data;
+static void connection_cb (ConIcConnection *ciconn, ConIcConnectionEvent *event, PluginInfo *self);
+static gboolean ensure_network(PluginInfo *self);
+static void save_config(PrivateVpnDetails *vpn_settings,int);
+void vpn_access_points_settings_dialog_response (GtkDialog *settings_dialog,
+ gint response,
+ PluginInfo *self);
+
+static void vpngui_connect_dialog( GtkButton *button,PluginInfo *self);
+static ConIcConnection *ciconn = NULL;
+static gboolean connecting = FALSE;
+static gboolean arewe_connected = FALSE;
+static gboolean show_settings = TRUE;
+static gboolean isvpngui_connected = FALSE;
+static gboolean show_disconnect_button = FALSE;
+
+/* Paths to configs. Ugly, but works... */
+char vpn_gconf_vpn_name[]=VPN_GCONF_VPN_NAME;
+char vpn_gconf_user[]=VPN_GCONF_USER;
+char vpn_gconf_passwd[]=VPN_GCONF_PASSWD;
+char vpn_gconf_passwd_obf[]=VPN_GCONF_PASSWD_OBF;
+char vpn_gconf_gwaddr[]=VPN_GCONF_GWADDR;
+char vpn_gconf_group[]=VPN_GCONF_GROUP;
+char vpn_gconf_secret[]=VPN_GCONF_SECRET;
+char vpn_gconf_secret_obf[]=VPN_GCONF_SECRET_OBF;
+char vpn_gconf_proxy_mode[]=VPN_GCONF_PROXY_MODE;
+char vpn_gconf_proxy_server[]=VPN_GCONF_PROXY_SERVER;
+char vpn_gconf_proxy_port[]=VPN_GCONF_PROXY_PORT;
+char vpn_gconf_proxy_autoconfig_url[]=VPN_GCONF_PROXY_AUTOCONFIG_URL;
+char vpn_gconf_proxy_ignore_hosts[]=VPN_GCONF_PROXY_IGNORE_HOSTS;
+
+char vpn_gconf_rekey_interval[]=VPN_GCONF_REKEY_INTERVAL;
+char vpn_gconf_nat_keepalive[]=VPN_GCONF_NAT_KEEPALIVE;
+/* Change the gconf paths for our settings according to vpn_ap (0...X) */
+void vpn_make_config_paths(int ap_no)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ char vpn_ap[1];
+ sprintf (vpn_ap,"%d",ap_no);
+
+ sprintf(vpn_gconf_vpn_name,VPN_GCONF_VPN_NAME,vpn_ap);
+ sprintf(vpn_gconf_user,VPN_GCONF_USER,vpn_ap);
+ sprintf(vpn_gconf_passwd,VPN_GCONF_PASSWD,vpn_ap);
+ sprintf(vpn_gconf_passwd_obf,VPN_GCONF_PASSWD_OBF,vpn_ap);
+ sprintf(vpn_gconf_gwaddr,VPN_GCONF_GWADDR,vpn_ap);
+ sprintf(vpn_gconf_group,VPN_GCONF_GROUP,vpn_ap);
+ sprintf(vpn_gconf_secret,VPN_GCONF_SECRET,vpn_ap);
+ sprintf(vpn_gconf_secret_obf,VPN_GCONF_SECRET_OBF,vpn_ap);
+ sprintf(vpn_gconf_proxy_mode,VPN_GCONF_PROXY_MODE,vpn_ap);
+ sprintf(vpn_gconf_proxy_server,VPN_GCONF_PROXY_SERVER,vpn_ap);
+ sprintf(vpn_gconf_proxy_port,VPN_GCONF_PROXY_PORT,vpn_ap);
+ sprintf(vpn_gconf_rekey_interval,VPN_GCONF_REKEY_INTERVAL,vpn_ap);
+ sprintf(vpn_gconf_nat_keepalive,VPN_GCONF_NAT_KEEPALIVE,vpn_ap);
+ sprintf(vpn_gconf_proxy_autoconfig_url,VPN_GCONF_PROXY_AUTOCONFIG_URL,vpn_ap);
+ sprintf(vpn_gconf_proxy_ignore_hosts,VPN_GCONF_PROXY_IGNORE_HOSTS,vpn_ap);
+}
+
+gboolean get_vpn_name_config(GList* list)//int ap_no,char **vpn_name)
+{
+ GConfClient *gconf = NULL;
+ char vpn_ap_no[1];
+ gconf = gconf_client_get_default();
+ int i;
+ for(i=0;i<g_list_length(list);i++)
+ {
+ vpn_data = ((struct VpnGuiListData*)g_list_nth_data(list,i));
+ vpn_data->vpn_name = NULL;
+ sprintf (vpn_ap_no,"%d",vpn_data->ap_no);
+ sprintf(vpn_gconf_vpn_name,VPN_GCONF_VPN_NAME,vpn_ap_no);
+ vpn_data->vpn_name = gconf_client_get_string(gconf, vpn_gconf_vpn_name, NULL);
+ if(vpn_data->vpn_name == NULL)
+ {
+ //g_free(vpn_data);
+ list = g_list_remove(list,vpn_data);
+ }
+ }
+ g_object_unref(gconf);
+ return TRUE;
+}
+
+/* Get the connection settings from saved configuration files */
+static void get_config(PrivateVpnDetails *vpn_settings,int ap_no)
+{
+ GConfClient *gconf = NULL;
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ g_return_if_fail(vpn_settings);
+ /* Fetch the correct AP paths based on vpn_ap variable */
+
+ vpn_make_config_paths(ap_no);
+ gconf = gconf_client_get_default();
+ vpn_settings->gwaddress = gconf_client_get_string(gconf, vpn_gconf_gwaddr, NULL);
+ vpn_settings->group = gconf_client_get_string(gconf, vpn_gconf_group, NULL);
+ vpn_settings->secret = gconf_client_get_string(gconf, vpn_gconf_secret, NULL);
+ vpn_settings->secret_obf = gconf_client_get_bool(gconf, vpn_gconf_secret_obf, NULL);
+ vpn_settings->username = gconf_client_get_string(gconf, vpn_gconf_user, NULL);
+ vpn_settings->vpn_name = gconf_client_get_string(gconf, vpn_gconf_vpn_name, NULL);
+ vpn_settings->password = "";
+ vpn_settings->password_obf = FALSE;
+ /* Should be asked from GUI */
+
+ vpn_settings->rekeyinterval = VPN_REKEY_INTERVAL;
+ vpn_settings->natkeepalive = VPN_NAT_KEEPALIVE;
+ vpn_settings->proxytype = gconf_client_get_string(gconf, vpn_gconf_proxy_mode, NULL);
+ vpn_settings->proxy_server = gconf_client_get_string(gconf, vpn_gconf_proxy_server, NULL);
+ vpn_settings->proxy_port = gconf_client_get_int(gconf, vpn_gconf_proxy_port, NULL);
+ vpn_settings->proxy_autoconfig_url = gconf_client_get_string(gconf, vpn_gconf_proxy_autoconfig_url, NULL);
+ vpn_settings->proxy_ignore_hosts = gconf_client_get_list(gconf, vpn_gconf_proxy_ignore_hosts,GCONF_VALUE_STRING, NULL);
+
+ g_object_unref(gconf);
+}
+
+static void plugin_callback (GtkWidget *Radio_button,
+ PluginInfoPrivate *priv)
+{
+
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ if(show_disconnect_button)
+ {
+ if(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(((struct VpnGuiListData*)g_list_nth_data(priv->list, priv->connected_vpn_ap_ui))->radio_button)))
+ {
+ gtk_button_set_label (GTK_BUTTON(priv->connect_button),"Disconnect");
+ gtk_widget_set_sensitive(priv->connect_button,TRUE);
+ /* If vpn is activated for a particular access point, then
+ * Delete button for that access point needs to be disabled.
+ * */
+ gtk_widget_set_sensitive(priv->delete_button,FALSE);
+ }
+ else
+ {
+ gtk_button_set_label (GTK_BUTTON(priv->connect_button),"Connect");
+ gtk_widget_set_sensitive(priv->connect_button,FALSE);
+ gtk_widget_set_sensitive(priv->delete_button,TRUE);
+ }
+ }
+ else
+ {
+ gtk_button_set_label (GTK_BUTTON(priv->connect_button),"Connect");
+ gtk_widget_set_sensitive(priv->connect_button,TRUE);
+ gtk_widget_set_sensitive(priv->delete_button,TRUE);
+ }
+
+}
+
+/******************************************************************************
+ * Forward declarations of callback functions.
+ */
+static void
+on_main_button_clicked (
+ GtkButton *button,
+ PluginInfo *self);
+
+/******************************************************************************
+ * The implementation of the plugin.
+ */
+
+HD_DEFINE_PLUGIN_MODULE (PluginInfo, vpngui_plugin, HD_TYPE_STATUS_MENU_ITEM);
+
+static void
+vpngui_plugin_class_finalize (PluginInfoClass *klass)
+{
+ TRACE ("");
+}
+
+static void
+vpngui_plugin_class_init (PluginInfoClass *klass)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ GObjectClass* object_class = G_OBJECT_CLASS (klass);
+ object_class->finalize = vpngui_destroy;
+ g_type_class_add_private (klass, sizeof (PluginInfoPrivate));
+ TRACE ("");
+ g_debug("Exiting %s", __PRETTY_FUNCTION__);
+}
+
+static void vpngui_destroy(GObject *object)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (object);
+
+ if(priv->vpn_notify)
+ {
+ g_object_unref(priv->vpn_notify);
+ priv->vpn_notify = NULL;
+ }
+ if(ciconn)
+ {
+ g_object_unref(ciconn);
+ ciconn = NULL;
+ }
+// G_OBJECT_CLASS(vpngui_plugin_parent_class)->finalize (object);
+
+ g_debug("Exiting %s", __PRETTY_FUNCTION__);
+}
+
+static DBusHandlerResult
+dbus_signal_filter(
+ DBusConnection *connection,
+ DBusMessage *message,
+ void *user_data)
+{
+ PluginInfo *self = (PluginInfo *)user_data;
+ if (dbus_message_is_signal (message, VPNC_DBUS_LISTENER_SERVICE, VPNC_DBUS_LISTENER_SIGNAL)) {
+ g_debug("Signal has been received in %s", __PRETTY_FUNCTION__);
+ DBusError error;
+ char *s = 0;
+ dbus_error_init (&error);
+ if (dbus_message_get_args (message, &error, DBUS_TYPE_STRING, &s,DBUS_TYPE_INVALID)){
+ if (g_str_equal("connected", s)) {
+ g_debug("connected state called");
+ set_state(self, VPN_CONNECTED);
+ } else if (g_str_equal("disconnected", s)) {
+ set_state(self, VPN_DISCONNECTED);
+ g_debug ("We have a end DBus message.");
+ } else {
+ g_debug("XXXX unknown state %s\n", s);
+ }
+ } else {
+ dbus_error_free (&error);
+ }
+ return DBUS_HANDLER_RESULT_HANDLED;
+ }
+ return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
+
+}
+
+gboolean register_dbus_signal_filter(
+ osso_context_t *context,
+ gpointer user_data)
+{
+
+ DBusConnection *bus = (DBusConnection*) osso_get_dbus_connection (context);
+ if (!bus) {
+ return FALSE;
+ }
+ dbus_bus_add_match (bus, VPNC_DBUS_LISTENER_TYPE, NULL);
+ if (!dbus_connection_add_filter (bus, dbus_signal_filter, user_data, NULL)) {
+ return FALSE;
+ }
+ return TRUE;
+}
+
+static void
+vpngui_plugin_init (PluginInfo *menu_item)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (menu_item);
+
+ TRACE ("");
+
+ /**********************************************************************
+ * Initializing osso
+ */
+ priv->osso_context = osso_initialize(PACKAGE, VERSION, FALSE, NULL);
+ if (!priv->osso_context) {
+ TRACE ("Error initializing osso");
+ }
+
+ /**********************************************************************
+ * Setting up a DBus listener, System call
+ */
+ if (!register_dbus_signal_filter (priv->osso_context, menu_item)) {
+ g_debug ("Unable to register DBUS filter function");
+ exit (1);
+ }
+ /**********************************************************************
+ * Setting up the locale.
+ */
+ bindtextdomain(GETTEXT_PACKAGE, PACKAGE_LOCALE_DIR);
+ bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8");
+ textdomain(GETTEXT_PACKAGE);
+ /**********************************************************************
+ * Creating widgets.
+ */
+
+ priv->icon = gtk_image_new_from_pixbuf(NULL);
+ priv->button = gtk_toggle_button_new();
+ priv->state = VPN_DISCONNECTED;
+ priv->show_connect_dialog = FALSE;
+ priv->vpnc_pid = 0;
+ priv->vpnc_watch_id = 0;
+ priv->old_ip = NULL;
+ priv->list = NULL;
+ priv->total_items = 0;
+ priv->connected_vpn_ap_gconf = VPN_DEFAULT_HIRO_VPN;
+
+ priv->pixbuf[PIXBUF_ACTIVE] = gdk_pixbuf_new_from_file(ICON_ACTIVE, NULL);
+ priv->pixbuf[PIXBUF_INACTIVE] = gdk_pixbuf_new_from_file(ICON_INACTIVE,NULL);
+ priv->pixbuf[PIXBUF_SUSPENDED] = gdk_pixbuf_new_from_file(ICON_SUSPENDED,NULL);
+ priv->pixbuf[PIXBUF_ACTIVE_SMALL] = gdk_pixbuf_new_from_file(ICON_ACTIVE_SMALL, NULL);
+ priv->pixbuf[PIXBUF_SUSPENDED_SMALL] = gdk_pixbuf_new_from_file(ICON_SUSPENDED_SMALL, NULL);
+ gtk_image_set_from_pixbuf(GTK_IMAGE(priv->icon),
+ priv->pixbuf[PIXBUF_INACTIVE]);
+ priv->show_icon = FALSE;
+
+ priv->container_hbox = gtk_hbox_new(FALSE, 0);
+ priv->vbox1 = gtk_vbox_new(FALSE, 0);
+ priv->vbox2 = gtk_vbox_new(FALSE, 0);
+
+ /*
+ * A button used as a menu item.
+ */
+ priv->button = hildon_button_new (
+ HILDON_SIZE_FINGER_HEIGHT,
+ HILDON_BUTTON_ARRANGEMENT_VERTICAL);
+ gtk_container_set_border_width(GTK_CONTAINER(priv->button), 3);
+
+ priv->sync_name_label = gtk_label_new("VPN");
+ gtk_misc_set_alignment(GTK_MISC(priv->sync_name_label), .0, .5);
+
+ priv->prof_name_label = gtk_label_new(" ");
+ gtk_misc_set_alignment(GTK_MISC(priv->prof_name_label), .0, .5);
+
+ gtk_widget_set_size_request(priv->icon,
+ STATUS_MENU_VPNGUI_ICON_SIZE,
+ STATUS_MENU_VPNGUI_ICON_SIZE);
+
+ gtk_container_add(GTK_CONTAINER(priv->button), priv->container_hbox);
+ gtk_box_pack_start(GTK_BOX(priv->container_hbox), priv->icon,
+ FALSE, TRUE, 0);
+ gtk_box_pack_start(GTK_BOX(priv->container_hbox), priv->vbox1, TRUE, TRUE, 0);
+ gtk_box_pack_start(GTK_BOX(priv->vbox1), priv->vbox2, TRUE, FALSE, 0);
+ gtk_box_pack_start(GTK_BOX(priv->vbox2), priv->sync_name_label, FALSE, FALSE, 0);
+ gtk_box_pack_start(GTK_BOX(priv->vbox2), priv->prof_name_label, FALSE, FALSE, 0);
+
+ priv->button2 = gtk_button_new();
+ gtk_button_set_label (GTK_BUTTON(priv->button2),"Connect");
+
+ gtk_container_add(GTK_CONTAINER(menu_item), priv->button);
+ gtk_widget_show_all (GTK_WIDGET(priv->button));
+ gtk_widget_show (GTK_WIDGET(menu_item));
+
+ /**********************************************************************
+ * Connecting signals.
+ */
+ g_signal_connect (priv->button, "clicked",
+ G_CALLBACK (on_main_button_clicked), menu_item);
+
+ /* Initialize configuration from gconf */
+ get_config(&priv->vpn_settings,priv->connected_vpn_ap_gconf);
+ priv->vpnc_config = NULL;
+ priv->vpn_notify = NULL;
+ /* Make a new connection */
+ ciconn = con_ic_connection_new ();
+ if (!ciconn) {
+ error_msg("Con_ic_connection_new() failed");
+ }
+ else
+ {
+ /* Setup event callbacks: route events -> connection_cb() */
+ /* Pass the userdata along */
+ g_signal_connect (ciconn, "connection-event", G_CALLBACK(connection_cb), menu_item);
+ /* err.. what? */
+ g_object_set (ciconn, "automatic-connection-events", TRUE, NULL);
+ }
+
+ /* While upgrading the component this cannot register to exisiting type.
+ * One way to avoid is to use dsme tool to shutdown hildon-status-menu
+ * or reboot
+ * */
+ priv->vpn_notify = g_object_new(VPN_TYPE_NOTIFY, NULL);
+ g_debug("Exiting %s", __PRETTY_FUNCTION__);
+
+}
+
+/* Reconnect the VPN */
+static gboolean do_reconnect(PluginInfo *self)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ return vpnc_restart(self);
+}
+
+/* Connection event magic */
+static void
+connection_cb (ConIcConnection *ciconn, ConIcConnectionEvent *event, PluginInfo *self)
+{
+ g_debug("Executing %s (%p, )", __PRETTY_FUNCTION__, event);
+ const gchar *iap_id, *bearer;
+ ConIcConnectionStatus status;
+ ConIcConnectionError error;
+ /* check the events */
+ /* g_assert(CON_IC_IS_CONNECTION_EVENT(event)); */
+ /* get the userdata */
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+ /* get the event info */
+ status = con_ic_connection_event_get_status(event);
+ error = con_ic_connection_event_get_error(event);
+ iap_id = con_ic_event_get_iap_id(CON_IC_EVENT(event));
+ bearer = con_ic_event_get_bearer_type(CON_IC_EVENT(event));
+
+ /* Error handling. Break out if there is a error...*/
+ switch (error) {
+ case CON_IC_CONNECTION_ERROR_NONE:
+ /* no error is good error :) */
+ break;
+ case CON_IC_CONNECTION_ERROR_INVALID_IAP:
+ error_msg ("CON_IC: INVALID_IAP (%s, %s, %i, %i)", iap_id, bearer, status, error);
+ arewe_connected = FALSE;
+ priv->have_network = FALSE;
+ connecting = FALSE;
+ break;
+ case CON_IC_CONNECTION_ERROR_CONNECTION_FAILED:
+ error_msg ("CON_IC: Connection failed (%s, %s, %i, %i)", iap_id, bearer, status, error);
+ arewe_connected = FALSE;
+ priv->have_network = FALSE;
+ connecting = FALSE;
+ break;
+ case CON_IC_CONNECTION_ERROR_USER_CANCELED:
+ error_msg ("CON_IC: User cancelled (%s, %s, %i, %i)", iap_id, bearer, status, error);
+ arewe_connected = FALSE;
+ priv->have_network = FALSE;
+ connecting = FALSE;
+ break;
+ default:
+ error_msg ("CON_IC: Unexpected error (%s, %s, %i, %i)", iap_id, bearer, status, error);
+ arewe_connected = FALSE;
+ priv->have_network = FALSE;
+ connecting = FALSE;
+ break;
+ }
+
+ /* Status events */
+ /* Unblock only if connected... (or error) */
+ switch (status) {
+ case CON_IC_STATUS_CONNECTED:
+ g_debug("%s: CONNECTED (%s, %s, %i, %i)", __PRETTY_FUNCTION__, iap_id, bearer, status, error);
+ arewe_connected = TRUE;
+ priv->have_network = TRUE;
+ connecting = FALSE;
+ break;
+ case CON_IC_STATUS_DISCONNECTED:
+ /* error_msg ("DISCONNECTED (%s, %s, %i, %i)", iap_id, bearer, status, error); */
+ g_debug("%s: DISCONNECTED (%s, %s, %i, %i)", __PRETTY_FUNCTION__, iap_id, bearer, status, error);
+ arewe_connected = FALSE;
+ priv->have_network = FALSE;
+ /* connecting = FALSE; */
+ if (priv->state == VPN_CONNECTED)
+ {
+ gtk_image_set_from_pixbuf(GTK_IMAGE(priv->icon),priv->pixbuf[PIXBUF_SUSPENDED]);
+ hd_status_plugin_item_set_status_area_icon (
+ HD_STATUS_PLUGIN_ITEM (self),
+ priv->pixbuf[PIXBUF_SUSPENDED_SMALL]);
+ priv->show_icon = FALSE;
+ isvpngui_connected = FALSE;
+ show_disconnect_button = TRUE; // To Display Connect in the button
+ /* Fix me : Hack : this is done if the network has moved from wireless to 3G */
+ gchar *wlan_addr =NULL;
+ wlan_addr = iface_addr("wlan0");
+ if(wlan_addr == NULL) /* if the connection is Point to Point Protocol */
+ wlan_addr = iface_addr("ppp0");
+ if(wlan_addr == NULL) /* if the connection is 3G network */
+ wlan_addr = iface_addr("gprs0");
+ /* if ip has changed, we are disconnecting */
+ if(wlan_addr != NULL)
+ {
+ if (priv->old_ip != NULL)
+ {
+ if (strcmp(priv->old_ip, wlan_addr))
+ {
+ if(wlan_addr!= NULL)
+ {
+ g_free(wlan_addr);
+ wlan_addr = NULL;
+ }
+ do_disconnect(self, FALSE);
+ }
+ }
+ if(wlan_addr!= NULL)
+ {
+ g_free(wlan_addr);
+ wlan_addr = NULL;
+ }
+ }
+ }
+ break;
+ case CON_IC_STATUS_DISCONNECTING:
+ g_debug("%s: DISCONNECTING (%s, %s, %i, %i)", __PRETTY_FUNCTION__, iap_id, bearer, status, error);
+ break;
+
+ default:
+ g_debug("%s: CON_IC: UNKNOWN STATUS (%s, %s, %i, %i)", __PRETTY_FUNCTION__, iap_id, bearer, status, error);
+ break;
+ }
+
+
+ if(priv->have_network) {
+ if (priv->show_connect_dialog) {
+ g_debug("%s: Showing connecton dialog...", __PRETTY_FUNCTION__);
+ priv->show_connect_dialog = FALSE;
+ vpngui_connect_dialog(GTK_BUTTON(priv->button2), self);
+ } else {
+ if(!isvpngui_connected)
+ {
+ g_debug("%s: Reconnecting...", __PRETTY_FUNCTION__);
+
+ do_reconnect(self);
+ }
+
+ }
+ }
+}
+
+/* Try to make sure we have network connection before launching vpnc. Using the new liconic */
+static gboolean ensure_network(PluginInfo *self)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ /* get the userdata */
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+
+ if (!ciconn) {
+ error_msg("Con_ic_connection_new() failed");
+ return FALSE;
+ }
+
+ if(priv->have_network) return TRUE;
+ connecting = TRUE;
+ /* Request for connection ... */
+ if (!con_ic_connection_connect (ciconn, CON_IC_CONNECT_FLAG_NONE)) {
+ error_msg ("Con_ic_connection_connect() failed.");
+ }
+
+ /* Loop here in event loop until connecting goes FALSE */
+ while (connecting) {
+ /* Iterate the main loop so that the signal can be called. */
+ if (g_main_context_pending (NULL)) {
+ g_main_context_iteration (NULL, FALSE);
+ }
+ }
+
+ /* Return TRUE/FALSE, depending how the events when :) */
+ g_debug("Exiting %s with res = %d", __PRETTY_FUNCTION__, arewe_connected);
+ return arewe_connected;
+}
+void save_vpn_configuration(PluginInfo *self,int ap_no)
+{
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+ gchar *message = NULL;
+ char *markup;
+ /* Fetch the correct info from gconf */
+ get_config(&priv->vpn_settings,ap_no);
+ /* Display the name of the Access point */
+ message = g_strdup(priv->vpn_settings.vpn_name);
+ markup = g_markup_printf_escaped ("<span color=\"#95EAEA\"><small>%s</small></span>", message);
+ gtk_label_set_markup (GTK_LABEL (priv->prof_name_label), markup);
+ g_free (markup);
+ g_free (message);
+ /* Is this really needed... */
+ priv->vpnc_config = "";
+
+}
+
+static int sort_data(gconstpointer a, gconstpointer b)
+{
+ struct VpnGuiListData* first = (struct VpnGuiListData*)a;
+ struct VpnGuiListData* second = (struct VpnGuiListData*)b;
+ gint ret = g_ascii_strcasecmp((char*)(first->vpn_name),(char*)(second->vpn_name));
+ return ret;
+}
+
+GList* get_vpn_config_list()
+{
+ GConfClient *gconf = NULL;
+ GSList *list =NULL;
+ GList *priv_list = NULL;
+ gconf = gconf_client_get_default();
+ list = gconf_client_all_dirs(gconf,VPN_GCONF_PATH,NULL);
+
+ int i;
+ for(i=0;i<g_slist_length(list);i++)
+ {
+ vpn_data= (struct VpnGuiListData*)malloc(sizeof(struct VpnGuiListData*));
+ int num ;
+ char *name = (char*)g_slist_nth_data(list,i);
+ sscanf(name,VPN_GCONF_AP_PATH_NO,&num);
+ sprintf(vpn_gconf_vpn_name,VPN_GCONF_VPN_NAME_NO,num);
+ vpn_data->vpn_name = gconf_client_get_string(gconf, vpn_gconf_vpn_name, NULL);
+ if(vpn_data->vpn_name == NULL)
+ {
+ if(vpn_data)
+ {
+ free(vpn_data);
+ vpn_data = NULL;
+ }
+ g_free(g_slist_nth_data(list,i));
+ continue;
+ }
+
+ vpn_data->ap_no = num;
+ priv_list = g_list_append(priv_list,vpn_data);
+ g_free(g_slist_nth_data(list,i));
+ }
+ g_slist_free(list);
+ g_object_unref(gconf);
+ if(g_list_length(priv_list) >1)
+ priv_list = g_list_sort(priv_list,sort_data);
+
+ return priv_list;
+}
+
+void vpn_settings_screen(PluginInfoPrivate *priv,int ap_no,gboolean show_new_vpn_ap)
+{
+ GtkWidget *dialog ;
+ GtkWidget *container_hbox, *vbox , *scrolledwindow;
+ GtkWidget *name_entry,*gw_entry, *group_entry, *secret_entry;
+ GtkWidget *proxy_server_entry, *proxy_port_entry;
+
+ gboolean show_settings_again = FALSE;
+
+ GtkWidget *obf_check_entry;
+ PrivateVpnDetails vpn_settings;
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+
+ get_config(&vpn_settings,ap_no);
+ dialog = gtk_dialog_new_with_buttons("Access point settings",
+ NULL,
+ GTK_DIALOG_MODAL ,
+ GTK_STOCK_OK,
+ GTK_RESPONSE_OK,
+ GTK_STOCK_CANCEL,
+ GTK_RESPONSE_CANCEL,
+ NULL);
+
+
+ container_hbox = gtk_hbox_new(FALSE, 0);
+ gtk_widget_set_size_request(container_hbox,300,400);
+ gtk_container_add(GTK_CONTAINER(GTK_DIALOG(dialog)->vbox), container_hbox);
+ scrolledwindow = hildon_pannable_area_new();
+ gtk_box_pack_start (GTK_BOX (container_hbox),scrolledwindow, TRUE, TRUE, 0);
+
+ vbox = gtk_vbox_new(FALSE, 0);
+ hildon_pannable_area_add_with_viewport(HILDON_PANNABLE_AREA(scrolledwindow),vbox);
+// gtk_box_pack_start(GTK_BOX(hbox), vbox, FALSE, FALSE, 6);
+ GtkSizeGroup *group = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
+
+ name_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ hildon_gtk_entry_set_input_mode(GTK_ENTRY(name_entry),HILDON_GTK_INPUT_MODE_FULL);
+ gw_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ hildon_gtk_entry_set_input_mode(GTK_ENTRY(gw_entry),HILDON_GTK_INPUT_MODE_FULL);
+ group_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ hildon_gtk_entry_set_input_mode(GTK_ENTRY(group_entry), HILDON_GTK_INPUT_MODE_FULL);
+ secret_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ hildon_gtk_entry_set_input_mode(GTK_ENTRY(secret_entry),HILDON_GTK_INPUT_MODE_FULL | HILDON_GTK_INPUT_MODE_INVISIBLE);
+ obf_check_entry = hildon_check_button_new(HILDON_SIZE_FINGER_HEIGHT);
+ gtk_button_set_label (GTK_BUTTON (obf_check_entry), "IPSec Secret obfuscated");
+ proxy_server_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ hildon_gtk_entry_set_input_mode(GTK_ENTRY(proxy_server_entry),HILDON_GTK_INPUT_MODE_FULL);
+ proxy_port_entry = hildon_number_editor_new(0, 65535);
+ int proxy_port = 8080;
+
+ GtkWidget *name_caption = hildon_caption_new(group,
+ "Name",
+ name_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+ GtkWidget *gw_caption = hildon_caption_new(group,
+ "Gateway address",
+ gw_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+ GtkWidget *group_caption = hildon_caption_new(group,
+ "IPSec Group",
+ group_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+ GtkWidget *secret_caption = hildon_caption_new(group,
+ "IPSec Secret",
+ secret_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+ GtkWidget *proxy_server_caption = hildon_caption_new(group,
+ "VPN HTTP(S) proxy host",
+ proxy_server_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+ GtkWidget *proxy_port_caption = hildon_caption_new(group,
+ "VPN HTTP(S) proxy port",
+ proxy_port_entry,
+ NULL,
+ HILDON_CAPTION_OPTIONAL);
+
+ gtk_box_pack_start (GTK_BOX(vbox),name_caption, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),gw_caption, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),group_caption, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),secret_caption, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),obf_check_entry, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),proxy_server_caption, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX(vbox),proxy_port_caption, TRUE, TRUE, 0);
+
+ if (vpn_settings.vpn_name) {
+ gtk_entry_set_text(GTK_ENTRY(name_entry), vpn_settings.vpn_name);
+ }
+ if (vpn_settings.gwaddress) {
+ gtk_entry_set_text(GTK_ENTRY(gw_entry), vpn_settings.gwaddress);
+ }
+ if (vpn_settings.group) {
+ gtk_entry_set_text(GTK_ENTRY(group_entry), vpn_settings.group);
+ }
+ if (vpn_settings.secret) {
+ gtk_entry_set_text(GTK_ENTRY(secret_entry), vpn_settings.secret);
+ }
+ hildon_check_button_set_active(HILDON_CHECK_BUTTON(obf_check_entry),vpn_settings.secret_obf);
+
+ if (vpn_settings.proxy_server) {
+ gtk_entry_set_text(GTK_ENTRY(proxy_server_entry), vpn_settings.proxy_server);
+ }
+ if (vpn_settings.proxy_port) {
+ proxy_port = vpn_settings.proxy_port;
+ }
+ hildon_number_editor_set_value(HILDON_NUMBER_EDITOR(proxy_port_entry), proxy_port);
+
+
+ gtk_widget_show_all(GTK_WIDGET(dialog));
+ if (gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_RESPONSE_OK) {
+ if(!strcmp(gtk_entry_get_text(GTK_ENTRY(name_entry)),""))
+ {
+ GtkWidget *error_dialog = gtk_dialog_new_with_buttons("Error Message",
+ NULL,
+ GTK_DIALOG_MODAL ,
+ GTK_STOCK_OK,
+ GTK_RESPONSE_OK,
+ GTK_STOCK_CANCEL,
+ GTK_RESPONSE_CANCEL,
+ NULL);
+ GtkWidget *hbox = gtk_hbox_new(FALSE, 0);
+ gtk_container_add(GTK_CONTAINER(GTK_DIALOG(error_dialog)->vbox), hbox);
+ GtkWidget *vbox = gtk_vbox_new(FALSE, 0);
+ gtk_box_pack_start(GTK_BOX(hbox), vbox, FALSE, FALSE, 6);
+ GtkWidget *label = gtk_label_new("Data is not saved as Name Entry was not given");
+ gtk_container_add(GTK_CONTAINER(GTK_BOX(vbox)), label);
+ gtk_widget_show_all(GTK_WIDGET(error_dialog));
+ gtk_dialog_run(GTK_DIALOG(error_dialog));
+ gtk_widget_destroy(GTK_WIDGET(error_dialog));
+
+ show_settings_again = TRUE;
+ }
+ if(!show_settings_again)
+ {
+ vpn_settings.vpn_name = g_strdup(gtk_entry_get_text(GTK_ENTRY(name_entry)));
+ vpn_settings.gwaddress = g_strdup(gtk_entry_get_text(GTK_ENTRY(gw_entry)));
+ vpn_settings.group = g_strdup(gtk_entry_get_text(GTK_ENTRY(group_entry)));
+ vpn_settings.secret = g_strdup(gtk_entry_get_text(GTK_ENTRY(secret_entry)));
+ vpn_settings.secret_obf = hildon_check_button_get_active(HILDON_CHECK_BUTTON(obf_check_entry));
+ vpn_settings.proxy_server = g_strdup(gtk_entry_get_text(GTK_ENTRY(proxy_server_entry)));
+ vpn_settings.proxy_port = hildon_number_editor_get_value(HILDON_NUMBER_EDITOR(proxy_port_entry));
+ if (g_str_equal(vpn_settings.proxy_server, "")) {
+ vpn_settings.proxytype = "none";
+ } else {
+ vpn_settings.proxytype = "manual";
+ }
+ if ( show_new_vpn_ap ){
+ priv->total_items++;
+ }
+
+ save_config(&vpn_settings,ap_no);
+ /* Enable the Connect Button, Delete Button,Settings Button */
+ gtk_widget_set_sensitive(priv->connect_button,TRUE);
+ gtk_widget_set_sensitive(priv->delete_button,TRUE);
+ gtk_widget_set_sensitive(priv->settings_button,TRUE);
+ }
+ }
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+ if(show_settings_again)
+ vpn_settings_screen(priv,ap_no,show_new_vpn_ap);
+}
+
+void delete_vpn_ap_settings(int ap_no)
+{
+ GConfClient *gconf = NULL;
+ gconf = gconf_client_get_default();
+ char dir[22];
+ sprintf(dir,VPN_GCONF_AP_PATH_NO,ap_no);
+ gconf_client_recursive_unset(gconf,dir,0,NULL);
+ g_object_unref(gconf);
+}
+
+void vpn_access_points_settings_dialog_response (GtkDialog *settings_dialog,
+ gint response,
+ PluginInfo *self)
+{
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+ gboolean show_new_vpn_ap =FALSE;
+ int ap_no_gui=0; /* Selected VPN access point.. From GUI */
+ int ap_no_gconf=0; /* VPN access point .. From GConf */
+ for(ap_no_gui=0;ap_no_gui<priv->total_items;ap_no_gui++)
+ {
+ if(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(((struct VpnGuiListData*)g_list_nth_data(priv->list,ap_no_gui))->radio_button)))
+ {
+ ap_no_gconf = ((struct VpnGuiListData*)g_list_nth_data(priv->list,ap_no_gui))->ap_no;
+ break;
+ }
+ }
+ int delete_data;
+ for(delete_data=0;delete_data<g_list_length(priv->list);delete_data++)
+ {
+ gtk_widget_destroy(GTK_WIDGET(((struct VpnGuiListData*)g_list_nth_data(priv->list,delete_data))->radio_button));
+ g_free((struct VpnGuiListData*)g_list_nth_data(priv->list,delete_data));
+ }
+ g_list_free(priv->list);
+ priv->list = NULL;
+ gtk_widget_destroy(GTK_WIDGET(settings_dialog));
+ switch (response)
+ {
+ case VPN_ACCESS_POINT_NEW:
+ /* random_no creation */
+ srand((unsigned)time(0));
+ ap_no_gconf = rand()%10000;
+ show_new_vpn_ap = TRUE;
+
+ case VPN_ACCESS_POINT_SETTINGS:
+ vpn_settings_screen(priv,ap_no_gconf,show_new_vpn_ap);
+ break;
+ case VPN_ACCESS_POINT_CONNECT:
+ priv->connected_vpn_ap_gconf = ap_no_gconf;
+ save_vpn_configuration(self,priv->connected_vpn_ap_gconf);
+ vpngui_connect_dialog(GTK_BUTTON(priv->button2), self);
+ break;
+ case VPN_ACCESS_POINT_DELETE:
+ {
+ delete_vpn_ap_settings(ap_no_gconf);
+ if(ap_no_gui == priv->connected_vpn_ap_ui)
+ {
+ priv->connected_vpn_ap_gconf = VPN_DEFAULT_HIRO_VPN;
+ gtk_label_set_text(GTK_LABEL(priv->prof_name_label)," ");
+ if(g_list_length(priv->list))
+ save_vpn_configuration(self,priv->connected_vpn_ap_gconf);
+ else
+ {
+ /* Disable the Connect Button, Delete Button,Settings Button */
+ gtk_widget_set_sensitive(priv->connect_button,FALSE);
+ gtk_widget_set_sensitive(priv->delete_button,FALSE);
+ gtk_widget_set_sensitive(priv->settings_button,FALSE);
+ }
+ }else if(ap_no_gui < priv->connected_vpn_ap_ui)
+ {
+ /* sometimes if configuration settings are done via schema, they do not get deleted.
+ * for this reason, we do this when list is populated.
+ * priv->connected_vpn_ap_ui--;
+ * */
+ }
+ }
+ break;
+ default :
+ break;
+ }
+
+}
+/**
+ * on_main_button_clicked:
+ *
+ * This function is called when the user clicks on the button added to the
+ * status menu. The function will properly start up the ui
+ * by showing the main dialog.
+ */
+static void
+on_main_button_clicked (
+ GtkButton *button,
+ PluginInfo *self)
+{
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+
+ priv->main_dialog = GTK_DIALOG(hildon_dialog_new());
+ gtk_window_set_modal (GTK_WINDOW(priv->main_dialog), TRUE);
+ g_object_set (G_OBJECT(priv->main_dialog),
+ "has-separator", FALSE,
+ NULL);
+ gtk_window_set_title (GTK_WINDOW(priv->main_dialog), "VPN Gateways");
+
+ GtkWidget * container_vbox = gtk_vbox_new (FALSE, 0);
+ priv->list = get_vpn_config_list();
+ priv->total_items = g_list_length(priv->list);
+
+ GtkWidget *scrolledwindow = hildon_pannable_area_new();
+ GtkWidget * radio_buttons_vbox = gtk_vbox_new (FALSE, 0);
+ int i;
+ gboolean first_item = TRUE;
+ priv->connected_vpn_ap_ui = VPN_DEFAULT_HIRO_VPN;
+
+ for(i=0;i<priv->total_items;i++)
+ {
+ vpn_data = ((struct VpnGuiListData*)g_list_nth_data(priv->list,i));
+ if(!first_item)
+ {
+ vpn_data->radio_button = hildon_gtk_radio_button_new (HILDON_SIZE_FINGER_HEIGHT,
+ gtk_radio_button_group(GTK_RADIO_BUTTON(((struct VpnGuiListData*)g_list_nth_data(priv->list,0))->radio_button)));
+ gtk_button_set_label (GTK_BUTTON (vpn_data->radio_button), vpn_data->vpn_name);
+ }
+ else
+ {
+ vpn_data->radio_button = hildon_gtk_radio_button_new (HILDON_SIZE_FINGER_HEIGHT,NULL);
+ gtk_button_set_label (GTK_BUTTON (vpn_data->radio_button), vpn_data->vpn_name);
+ first_item = FALSE;
+ }
+
+ if(priv->connected_vpn_ap_gconf == vpn_data->ap_no)
+ priv->connected_vpn_ap_ui = i;
+
+
+ gtk_box_pack_start (GTK_BOX(radio_buttons_vbox),vpn_data->radio_button, TRUE, TRUE, 0);
+
+ g_signal_connect_after (vpn_data->radio_button, "clicked",
+ G_CALLBACK (plugin_callback),
+ priv);
+
+ }
+ hildon_pannable_area_add_with_viewport(HILDON_PANNABLE_AREA(scrolledwindow),radio_buttons_vbox);
+ gtk_box_pack_start (GTK_BOX (container_vbox),scrolledwindow, TRUE, TRUE, 0);
+ gtk_box_pack_start (GTK_BOX (priv->main_dialog->vbox),container_vbox, TRUE, TRUE, 0);
+
+ gtk_dialog_add_button (priv->main_dialog,
+ "New",VPN_ACCESS_POINT_NEW);
+ priv->delete_button = gtk_dialog_add_button (priv->main_dialog,
+ "Delete",VPN_ACCESS_POINT_DELETE);
+ priv->settings_button = gtk_dialog_add_button (priv->main_dialog,
+ "Settings",VPN_ACCESS_POINT_SETTINGS);
+ priv->connect_button = gtk_dialog_add_button (priv->main_dialog,
+ "Connect",VPN_ACCESS_POINT_CONNECT);
+ g_signal_connect (G_OBJECT (priv->main_dialog),
+ "response",
+ G_CALLBACK(vpn_access_points_settings_dialog_response),
+ self);
+ if(priv->total_items)
+ {
+ gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(((struct VpnGuiListData*)g_list_nth_data(priv->list,priv->connected_vpn_ap_ui))->radio_button),TRUE);
+ plugin_callback(GTK_WIDGET(((struct VpnGuiListData*)g_list_nth_data(priv->list,priv->connected_vpn_ap_ui))->radio_button),priv);
+ }
+ else
+ {
+ /* Disable the Connect Button, Delete Button,Settings Button */
+ gtk_widget_set_sensitive(priv->connect_button,FALSE);
+ gtk_widget_set_sensitive(priv->delete_button,FALSE);
+ gtk_widget_set_sensitive(priv->settings_button,FALSE);
+ }
+
+ gtk_widget_show_all (GTK_WIDGET(priv->main_dialog));
+
+
+}
+
+/* Save applet configs to file(s) */
+static void save_config(PrivateVpnDetails *vpn_settings,int ap_no)
+{
+ GConfClient *gconf = NULL;
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+
+ g_return_if_fail(vpn_settings);
+ /* Fetch the correct AP paths based on vpn_ap variable */
+ vpn_make_config_paths(ap_no);
+ gconf = gconf_client_get_default();
+ if (vpn_settings->gwaddress) {
+ gconf_client_set_string(gconf, vpn_gconf_gwaddr,
+ vpn_settings->gwaddress, NULL);
+ }
+ if (vpn_settings->group) {
+ gconf_client_set_string(gconf, vpn_gconf_group, vpn_settings->group, NULL);
+ }
+ if (vpn_settings->secret) {
+ gconf_client_set_string(gconf, vpn_gconf_secret, vpn_settings->secret, NULL);
+ }
+ gconf_client_set_bool(gconf, vpn_gconf_secret_obf, vpn_settings->secret_obf, NULL);
+ if (vpn_settings->username) {
+ gconf_client_set_string(gconf, vpn_gconf_user, vpn_settings->username, NULL);
+ }
+ if (vpn_settings->vpn_name) {
+ gconf_client_set_string(gconf, vpn_gconf_vpn_name, vpn_settings->vpn_name, NULL);
+ }
+
+ if (vpn_settings->proxytype) {
+ gconf_client_set_string(gconf, vpn_gconf_proxy_mode, vpn_settings->proxytype, NULL);
+ }
+ if (vpn_settings->proxy_server) {
+ gconf_client_set_string(gconf, vpn_gconf_proxy_server, vpn_settings->proxy_server, NULL);
+ }
+ if (vpn_settings->proxy_port) {
+ gconf_client_set_int(gconf, vpn_gconf_proxy_port, vpn_settings->proxy_port, NULL);
+ }
+ if (vpn_settings->proxy_autoconfig_url) {
+ gconf_client_set_string(gconf, vpn_gconf_proxy_autoconfig_url, vpn_settings->proxy_autoconfig_url, NULL);
+ }
+/*
+ * if (vpn_settings->proxy_ignore_hosts) {
+ * gconf_client_set_list(gconf, vpn_gconf_proxy_ignore_hosts, GCONF_VALUE_STRING, vpn_settings->proxy_ignore_hosts, NULL);
+ * }
+ * */
+ g_object_unref(gconf);
+ g_debug("Exiting %s", __PRETTY_FUNCTION__);
+}
+
+static void set_proxy(PluginInfoPrivate *priv)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ if (! priv->vpn_settings.proxytype || g_str_equal(priv->vpn_settings.proxytype, "none")) {
+ return;
+ }
+ const gchar* proxy_server = (NULL == priv->vpn_settings.proxy_server) ? "" : priv->vpn_settings.proxy_server;
+ GConfClient *gconf = gconf_client_get_default();
+ GConfChangeSet *gcs = gconf_change_set_new();
+
+ gconf_change_set_set_string(gcs, "/system/proxy/mode", priv->vpn_settings.proxytype);
+ gconf_change_set_set_bool(gcs, "/system/http_proxy/use_http_proxy", TRUE);
+ gconf_change_set_set_string(gcs, "/system/http_proxy/host", proxy_server);
+ gconf_change_set_set_int(gcs, "/system/http_proxy/port", priv->vpn_settings.proxy_port);
+ gconf_change_set_set_string(gcs, "/system/proxy/ftp_host", proxy_server);
+ gconf_change_set_set_int(gcs, "/system/proxy/ftp_port", priv->vpn_settings.proxy_port);
+ gconf_change_set_set_string(gcs, "/system/proxy/secure_host", proxy_server);
+ gconf_change_set_set_int(gcs, "/system/proxy/secure_port", priv->vpn_settings.proxy_port);
+ gconf_change_set_set_list(gcs, "/system/http_proxy/ignore_hosts", GCONF_VALUE_STRING, priv->vpn_settings.proxy_ignore_hosts);
+ gconf_change_set_set_string(gcs, "/system/proxy/autoconfig_url", (NULL == priv->vpn_settings.proxy_autoconfig_url) ? "" : priv->vpn_settings.proxy_autoconfig_url);
+ priv->vpn_settings.proxy_saved = gconf_client_reverse_change_set(gconf, gcs, NULL);
+ gconf_client_commit_change_set(gconf, gcs, FALSE, NULL);
+
+ gconf_change_set_unref (gcs);
+ g_object_unref(gconf);
+ g_debug("Returning %s", __PRETTY_FUNCTION__);
+}
+
+static void restore_proxy(PluginInfoPrivate *priv)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ if (g_str_equal(priv->vpn_settings.proxytype, "none")) {
+ return;
+ }
+ GConfClient *gconf = gconf_client_get_default();
+ if(priv->vpn_settings.proxy_saved)
+ gconf_client_commit_change_set(gconf, priv->vpn_settings.proxy_saved, FALSE, NULL);
+
+ g_object_unref(gconf);
+ g_debug("Returning %s", __PRETTY_FUNCTION__);
+}
+
+static gchar *iface_addr(const gchar *iface)
+{
+ struct ifreq ifr;
+ int fd = socket(AF_INET, SOCK_DGRAM, 0);
+ if (fd < 0)
+ return NULL;
+ strncpy(ifr.ifr_name, iface, sizeof ifr.ifr_name);
+ if (ioctl(fd, SIOCGIFADDR, &ifr ) < 0) {
+ close(fd);
+ return NULL;
+ }
+ close(fd);
+ return g_strdup(inet_ntoa(((struct sockaddr_in *) &ifr.ifr_addr)->sin_addr));
+}
+
+/* Run the vpnc command */
+
+static gboolean do_connect(PluginInfo *self)
+{
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ gboolean success = FALSE;
+
+ if (vpnc_config_write(self)) {
+ success = vpnc_start(self);
+ }
+ /* FIXME: XXXX now that vpnc runs async, the unlink needs to be delayed
+ * * * until vpnc has had a chance to read it.. this needs to move elsewhere
+ * * */
+#if 0
+ unlink(priv->vpnc_config);
+#endif
+
+ return success;
+}
+
+/* Disconnect the VPN */
+static gboolean do_disconnect(PluginInfo *self, const gboolean forced)
+{
+ g_debug("Executing %s, forced = %d", __PRETTY_FUNCTION__, forced);
+ return vpnc_stop(self, forced);
+}
+
+
+void set_state(PluginInfo *self, int state)
+{
+ PluginInfoPrivate *priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+ g_debug("Executing %s, state = %d", __PRETTY_FUNCTION__, state);
+ priv->state = state;
+ gchar *sip_command = NULL;
+ switch (state) {
+ case VPN_CONNECTING:
+ gtk_widget_set_sensitive(priv->button, FALSE);
+ break;
+ case VPN_CONNECTED:
+ save_config(&priv->vpn_settings,priv->connected_vpn_ap_gconf);
+ set_proxy(priv);
+ hd_status_plugin_item_set_status_area_icon (
+ HD_STATUS_PLUGIN_ITEM (self),
+ priv->pixbuf[PIXBUF_ACTIVE_SMALL]);
+ priv->show_icon = TRUE;
+ gtk_image_set_from_pixbuf(GTK_IMAGE(priv->icon),
+ priv->pixbuf[PIXBUF_ACTIVE]);
+
+ isvpngui_connected = TRUE;
+ show_disconnect_button = TRUE;
+ show_settings = FALSE;
+ gtk_button_set_label (GTK_BUTTON(priv->button2),"Disconnect");
+
+ gchar *addr = iface_addr("tun0");
+ g_object_set(priv->vpn_notify, "ip", addr, NULL);
+ /* Temporary hack for enalbing sip calls while connected via VPN */
+ sip_command = g_strdup_printf("for i in `run-standalone.sh mc-tool-hiro list` \n \
+ do \
+ if [ \"`run-standalone.sh mc-tool-hiro show $i|grep Display|cut -f2 -d':'`\" == \" Nokia\" ];then \n\
+ run-standalone.sh mc-tool-hiro request $i offline \n \
+ run-standalone.sh mc-tool-hiro update $i string:local-ip-address=%s \n \
+ run-standalone.sh mc-tool-hiro enable $i \n \
+ sleep 1 \n \
+ run-standalone.sh mc-tool-hiro request $i online \n \
+ fi \n \
+ done",addr);
+ system(sip_command);
+ if(sip_command)
+ g_free(sip_command);
+
+ gtk_widget_destroy(GTK_WIDGET(priv->banner));
+ hildon_banner_show_information(GTK_WIDGET(priv->button), NULL, "VPN activated.");
+ gtk_widget_set_sensitive(priv->button, TRUE);
+
+ gchar *wlan_addr =NULL;
+ wlan_addr = iface_addr("wlan0");
+ if(wlan_addr == NULL) // if the connection is Point to Point Protocol
+ wlan_addr = iface_addr("ppp0");
+ if(wlan_addr == NULL) // if the connection is
+ wlan_addr = iface_addr("gprs0"); // 3G network
+ /* if ip has changed, we are disconnecting */
+ if (priv->old_ip != NULL)
+ {
+ if (strcmp(priv->old_ip, wlan_addr))
+ {
+
+ strcpy(priv->old_ip, wlan_addr);
+ if(addr != NULL)
+ {
+ g_free(addr);
+ addr = NULL;
+ }
+ if(wlan_addr!= NULL)
+ {
+ g_free(wlan_addr);
+ wlan_addr = NULL;
+ }
+ do_disconnect(self, FALSE);
+ }
+ }
+ else
+ {
+ priv->old_ip = g_malloc((strlen(wlan_addr) + 2) * sizeof(gchar));
+ strcpy(priv->old_ip, wlan_addr);
+ }
+ if(addr != NULL)
+ {
+ g_free(addr);
+ addr = NULL;
+ }
+ if(wlan_addr != NULL)
+ {
+ g_free(wlan_addr);
+ wlan_addr = NULL;
+ }
+
+ break;
+ case VPN_FORCED_DISCONNECTING:
+
+ priv->show_connect_dialog = TRUE;
+ if(priv->old_ip != NULL)
+ {
+ g_free(priv->old_ip);
+ priv->old_ip = NULL;
+ }
+ case VPN_DISCONNECTING:
+ if(priv->old_ip != NULL)
+ {
+ g_free(priv->old_ip);
+ priv->old_ip = NULL;
+ }
+ gtk_widget_set_sensitive(priv->button, FALSE);
+ priv->banner = hildon_banner_show_animation (
+ GTK_WIDGET(priv->button), NULL, "Disconnecting...");
+ break;
+ case VPN_CONNECT_FAILED:
+ gtk_widget_destroy(GTK_WIDGET(priv->banner));
+ priv->state = VPN_DISCONNECTED;
+ hildon_banner_show_information(GTK_WIDGET(priv->button),
+ NULL, "Connecting failed");
+ gtk_widget_set_sensitive(priv->button, TRUE);
+ restore_proxy(priv);
+ break;
+ case VPN_DISCONNECTED:
+
+ hd_status_plugin_item_set_status_area_icon (
+ HD_STATUS_PLUGIN_ITEM (self),
+ NULL);
+ priv->show_icon = FALSE;
+
+ gtk_image_set_from_pixbuf(GTK_IMAGE(priv->icon),
+ priv->pixbuf[PIXBUF_INACTIVE]);
+ if(priv->old_ip != NULL)
+ {
+ g_free(priv->old_ip);
+ priv->old_ip = NULL;
+ }
+ restore_proxy(priv);
+ isvpngui_connected = FALSE;
+ show_disconnect_button = FALSE;
+ show_settings = TRUE;
+ gtk_button_set_label (GTK_BUTTON(priv->button2),"Connect");
+ gtk_widget_destroy(GTK_WIDGET(priv->banner));
+ hildon_banner_show_information(GTK_WIDGET(priv->button),
+ NULL, "VPN disconnected.");
+ gtk_widget_set_sensitive(priv->button, TRUE);
+
+ g_object_set(priv->vpn_notify, "ip", "", NULL);
+
+ // have to remove this hack ..
+ sip_command = g_strdup_printf("for i in `run-standalone.sh mc-tool-hiro list` \n \
+ do \
+ if [ \"`run-standalone.sh mc-tool-hiro show $i|grep Display|cut -f2 -d':'`\" == \" Nokia\" ];then \n\
+ run-standalone.sh mc-tool-hiro request $i offline \n \
+ run-standalone.sh mc-tool-hiro update $i clear:local-ip-address \n \
+ run-standalone.sh mc-tool-hiro enable $i \n \
+ sleep 1 \n \
+ run-standalone.sh mc-tool-hiro request $i online \n \
+ fi \n \
+ done");
+ system(sip_command);
+ if(sip_command)
+ g_free(sip_command);
+ break;
+ default:
+// error_msg("Unknown state request %d", state);
+ g_debug("Unknown state request %d", state);
+ break;
+ }
+ g_debug("Exiting %s, state = %d", __PRETTY_FUNCTION__, state);
+}
+
+static void vpngui_connect_dialog( GtkButton *button,
+ PluginInfo *self)
+{
+ PluginInfoPrivate *priv;
+ GtkDialog *dialog;
+ g_debug("Executing %s", __PRETTY_FUNCTION__);
+ priv = VPNGUI_PLUGIN_GET_PRIVATE (self);
+ GtkWidget *parent = NULL;
+ parent = gtk_widget_get_toplevel (GTK_WIDGET (self));
+ gtk_widget_hide(parent);
+ if(show_settings)
+ {
+ if(priv->vpn_notify == NULL)
+ {
+ hildon_banner_show_animation (NULL, NULL, "You have to REBOOT the device once installation of vpn is done");
+ return;
+ }
+ GtkWidget *generic_label;
+ GtkWidget *container_hbox, *container_vbox;
+ GtkWidget *username_entry, *passwd_entry;
+
+ if (ensure_network(self) == FALSE || priv->have_network == FALSE) {
+ error_msg("Setting up network connection failed");
+ hildon_banner_show_information(NULL, NULL, "Setting up network connection failed");
+ return;
+ }
+
+ dialog = GTK_DIALOG(gtk_dialog_new_with_buttons("VPN Authentication",
+ NULL,
+ GTK_DIALOG_MODAL,
+ GTK_STOCK_OK,
+ GTK_RESPONSE_OK,
+ GTK_STOCK_CANCEL,
+ GTK_RESPONSE_REJECT,
+ NULL));
+ container_hbox = gtk_hbox_new(FALSE, 0);
+ gtk_container_add(GTK_CONTAINER(GTK_DIALOG(dialog)->vbox), container_hbox);
+ container_vbox = gtk_vbox_new(FALSE, 0);
+ gtk_box_pack_start(GTK_BOX(container_hbox), container_vbox, FALSE, FALSE, 6);
+ generic_label = gtk_label_new("Username:");
+ gtk_container_add(GTK_CONTAINER(container_vbox), generic_label);
+ generic_label = gtk_label_new("Password");
+ gtk_container_add(GTK_CONTAINER(container_vbox), generic_label);
+ container_vbox = gtk_vbox_new(FALSE, 0);
+ gtk_box_pack_start(GTK_BOX(container_hbox), container_vbox, FALSE, FALSE, 6);
+
+ username_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ gchar* username =NULL;
+ hildon_gtk_entry_set_input_mode (GTK_ENTRY(username_entry), HILDON_GTK_INPUT_MODE_FULL);
+ if (priv->vpn_settings.username) {
+ username = g_strdup(priv->vpn_settings.username);
+ gtk_entry_set_text(GTK_ENTRY(username_entry), username);
+ }
+ gtk_container_add(GTK_CONTAINER(container_vbox), username_entry);
+ passwd_entry = hildon_entry_new(HILDON_SIZE_FINGER_HEIGHT);
+ gtk_entry_set_activates_default(GTK_ENTRY(passwd_entry), TRUE);
+ hildon_gtk_entry_set_input_mode (GTK_ENTRY(passwd_entry), HILDON_GTK_INPUT_MODE_NUMERIC | HILDON_GTK_INPUT_MODE_INVISIBLE);
+ gtk_container_add(GTK_CONTAINER(container_vbox), passwd_entry);
+ if (priv->vpn_settings.username) {
+ gtk_widget_grab_focus(GTK_WIDGET(passwd_entry));
+ }
+ gtk_dialog_set_default_response(dialog, GTK_RESPONSE_OK);
+ gtk_widget_show_all(GTK_WIDGET(dialog));
+
+ if (gtk_dialog_run(dialog) == GTK_RESPONSE_OK) {
+ priv->vpn_settings.username = g_strdup(gtk_entry_get_text(GTK_ENTRY(username_entry)));
+ priv->vpn_settings.password = g_strdup(gtk_entry_get_text(GTK_ENTRY(passwd_entry)));
+ if(!strcmp(priv->vpn_settings.password,"")) //for empty password
+ {
+ hildon_banner_show_information(GTK_WIDGET(priv->button),
+ NULL, "Password is Empty");
+ if(username)
+ g_free(username);
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+ return;
+ }
+ priv->banner = hildon_banner_show_animation (GTK_WIDGET(parent),
+ NULL, "Connecting...");
+ do_connect(self);
+ }
+
+ if(username)
+ g_free(username);
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+ }
+ else
+ {
+ dialog = GTK_DIALOG(hildon_note_new_confirmation(NULL,
+ (gchar*)"Disconnect VPN?"));
+ if (gtk_dialog_run(dialog) == GTK_RESPONSE_OK) {
+ do_disconnect(self, FALSE);
+ }
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+ }
+}
+