[network-manager-openvpn/rm-userset] auth-dialog: port to NM 0.9



commit 442d0ed6272a9a02d234823e7986baa9d4a84810
Author: Dan Williams <dcbw redhat com>
Date:   Fri Feb 11 00:16:29 2011 -0600

    auth-dialog: port to NM 0.9

 auth-dialog/Makefile.am |   13 +-
 auth-dialog/main.c      |  326 ++++++++++++++++++++++-------------------------
 2 files changed, 157 insertions(+), 182 deletions(-)
---
diff --git a/auth-dialog/Makefile.am b/auth-dialog/Makefile.am
index 5d671f0..609c963 100644
--- a/auth-dialog/Makefile.am
+++ b/auth-dialog/Makefile.am
@@ -3,7 +3,6 @@ libexec_PROGRAMS = nm-openvpn-auth-dialog
 nm_openvpn_auth_dialog_CPPFLAGS =			\
 	$(GTHREAD_CFLAGS)			\
 	$(GTK_CFLAGS)				\
-	$(GCONF_CFLAGS)				\
 	$(NETWORK_MANAGER_CFLAGS)		\
 	$(GNOMEKEYRING_CFLAGS) \
 	-I$(top_srcdir)/
@@ -16,14 +15,14 @@ nm_openvpn_auth_dialog_CPPFLAGS =			\
 	-DGNOMELOCALEDIR=\"$(datadir)/locale\"	\
 	-DVERSION=\"$(VERSION)\"
 
-nm_openvpn_auth_dialog_SOURCES =			\
-	main.c					\
-	gnome-two-password-dialog.c		\
+nm_openvpn_auth_dialog_SOURCES = \
+	main.c \
+	gnome-two-password-dialog.c \
 	gnome-two-password-dialog.h
 
-nm_openvpn_auth_dialog_LDADD =			\
-	$(GTK_LIBS)				\
-	$(GCONF_LIBS)				\
+nm_openvpn_auth_dialog_LDADD = \
+	$(GTK_LIBS) \
+	$(NETWORK_MANAGER_LIBS) \
 	$(top_builddir)/common-gnome/libnm-openvpn-common-gnome.la \
 	$(top_builddir)/common/libnm-openvpn-common.la
 
diff --git a/auth-dialog/main.c b/auth-dialog/main.c
index 85a324b..45eb705 100644
--- a/auth-dialog/main.c
+++ b/auth-dialog/main.c
@@ -26,72 +26,67 @@
 #include <config.h>
 #endif
 
+#include <errno.h>
 #include <string.h>
 #include <stdlib.h>
 #include <glib/gi18n.h>
 #include <gtk/gtk.h>
-#include <gconf/gconf-client.h>
 #include <gnome-keyring.h>
+#include <gnome-keyring-memory.h>
 #include <nm-setting-vpn.h>
 #include <nm-setting-connection.h>
+#include <nm-vpn-plugin-utils.h>
 
 #include "common-gnome/keyring-helpers.h"
 #include "common/utils.h"
 #include "src/nm-openvpn-service.h"
 #include "gnome-two-password-dialog.h"
 
-typedef struct {
-	char *vpn_uuid;
-	char *vpn_name;
-
-	gboolean need_password;
-	char *password;
-
-	gboolean need_certpass;
-	char *certpass;
-} PasswordsInfo;
-
-static void
-clear_secrets (PasswordsInfo *info)
-{
-	if (info->password) {
-		memset (info->password, 0, strlen (info->password));
-		g_free (info->password);
-	}
-	if (info->certpass) {
-		memset (info->certpass, 0, strlen (info->certpass));
-		g_free (info->certpass);
-	}
-}
-
 static gboolean
-get_secrets (PasswordsInfo *info, gboolean retry)
+get_secrets (const char *vpn_name,
+             const char *vpn_uuid,
+             gboolean need_password,
+             gboolean need_certpass,
+             gboolean retry,
+             gboolean allow_interaction,
+             const char *in_pass,
+             char **out_password,
+             const char *in_certpass,
+             char **out_certpass)
 {
 	GnomeTwoPasswordDialog *dialog;
 	gboolean is_session = TRUE;
-	char *prompt;
+	char *prompt, *password = NULL, *certpass = NULL;
 	gboolean success = FALSE, need_secret = FALSE;
 
-	g_return_val_if_fail (info->vpn_uuid != NULL, FALSE);
-	g_return_val_if_fail (info->vpn_name != NULL, FALSE);
+	g_return_val_if_fail (vpn_name != NULL, FALSE);
+	g_return_val_if_fail (vpn_uuid != NULL, FALSE);
+	g_return_val_if_fail (out_password != NULL, FALSE);
+	g_return_val_if_fail (out_certpass != NULL, FALSE);
 
-	if (info->need_password) {
-		info->password = keyring_helpers_lookup_secret (info->vpn_uuid, NM_OPENVPN_KEY_PASSWORD, &is_session);
-		if (!info->password)
+	if (need_password) {
+		if (in_pass)
+			password = gnome_keyring_memory_strdup (in_pass);
+		else
+			password = keyring_helpers_lookup_secret (vpn_uuid, NM_OPENVPN_KEY_PASSWORD, &is_session);
+		if (!password)
 			need_secret = TRUE;
 	}
 
-	if (info->need_certpass) {
-		info->certpass = keyring_helpers_lookup_secret (info->vpn_uuid, NM_OPENVPN_KEY_CERTPASS, &is_session);
-		if (!info->certpass)
+	if (need_certpass) {
+		if (in_certpass)
+			certpass = gnome_keyring_memory_strdup (in_certpass);
+		else
+			certpass = keyring_helpers_lookup_secret (vpn_uuid, NM_OPENVPN_KEY_CERTPASS, &is_session);
+		if (!certpass)
 			need_secret = TRUE;
 	}
 
 	/* Have all passwords and we're not supposed to ask the user again */
-	if (!need_secret && !retry)
+	if ((!need_secret && !retry) || !allow_interaction)
 		return TRUE;
 
-	prompt = g_strdup_printf (_("You need to authenticate to access the Virtual Private Network '%s'."), info->vpn_name);
+	prompt = g_strdup_printf (_("You need to authenticate to access the Virtual Private Network '%s'."), vpn_name);
 	dialog = GNOME_TWO_PASSWORD_DIALOG (gnome_two_password_dialog_new (_("Authenticate VPN"), prompt, NULL, NULL, FALSE));
 	g_free (prompt);
 
@@ -101,7 +96,7 @@ get_secrets (PasswordsInfo *info, gboolean retry)
 	gnome_two_password_dialog_set_show_remember (dialog, TRUE);
 
 	/* If nothing was found in the keyring, default to not remembering any secrets */
-	if (info->password || info->certpass) {
+	if (password || certpass) {
 		/* Otherwise set default remember based on which keyring the secrets were found in */
 		if (is_session)
 			gnome_two_password_dialog_set_remember (dialog, GNOME_TWO_PASSWORD_DIALOG_REMEMBER_SESSION);
@@ -111,29 +106,37 @@ get_secrets (PasswordsInfo *info, gboolean retry)
 		gnome_two_password_dialog_set_remember (dialog, GNOME_TWO_PASSWORD_DIALOG_REMEMBER_NOTHING);
 
 	/* pre-fill dialog with the password */
-	if (info->need_password && info->need_certpass) {
+	if (need_password && need_certpass) {
 		gnome_two_password_dialog_set_show_password_secondary (dialog, TRUE);
 		gnome_two_password_dialog_set_password_secondary_label (dialog, _("Certificate pass_word:") );
 
 		/* if retrying, put in the passwords from the keyring */
-		if (info->password)
-			gnome_two_password_dialog_set_password (dialog, info->password);
-		if (info->certpass)
-			gnome_two_password_dialog_set_password_secondary (dialog, info->certpass);
+		if (password)
+			gnome_two_password_dialog_set_password (dialog, password);
+		if (certpass)
+			gnome_two_password_dialog_set_password_secondary (dialog, certpass);
 	} else {
 		gnome_two_password_dialog_set_show_password_secondary (dialog, FALSE);
-		if (info->need_password) {
+		if (need_password) {
 			/* if retrying, put in the passwords from the keyring */
-			if (info->password)
-				gnome_two_password_dialog_set_password (dialog, info->password);
-		} else if (info->need_certpass) {
+			if (password)
+				gnome_two_password_dialog_set_password (dialog, password);
+		} else if (need_certpass) {
 			gnome_two_password_dialog_set_password_primary_label (dialog, _("Certificate password:"));
 			/* if retrying, put in the passwords from the keyring */
-			if (info->certpass)
-				gnome_two_password_dialog_set_password (dialog, info->certpass);
+			if (certpass)
+				gnome_two_password_dialog_set_password (dialog, certpass);
 		}
 	}
-	clear_secrets (info);
+
+	if (password) {
+		memset (password, 0, strlen (password));
+		gnome_keyring_memory_free (password);
+	}
+	if (certpass) {
+		memset (certpass, 0, strlen (certpass));
+		gnome_keyring_memory_free (certpass);
+	}
 
 	gtk_widget_show (GTK_WIDGET (dialog));
 
@@ -141,12 +144,13 @@ get_secrets (PasswordsInfo *info, gboolean retry)
 		gboolean save = FALSE;
 		char *keyring = NULL;
 
-		if (info->need_password)
-			info->password = g_strdup (gnome_two_password_dialog_get_password (dialog));
-		if (info->need_certpass) {
-			info->certpass = g_strdup (info->need_password ? 
-								  gnome_two_password_dialog_get_password_secondary (dialog) :
-								  gnome_two_password_dialog_get_password (dialog));
+		if (need_password)
+			*out_password = gnome_keyring_memory_strdup (gnome_two_password_dialog_get_password (dialog));
+		if (need_certpass) {
+			if (need_password)
+				*out_certpass = gnome_keyring_memory_strdup (gnome_two_password_dialog_get_password_secondary (dialog));
+			else
+				*out_certpass = gnome_keyring_memory_strdup (gnome_two_password_dialog_get_password (dialog));
 		}
 
 		switch (gnome_two_password_dialog_get_remember (dialog)) {
@@ -161,13 +165,13 @@ get_secrets (PasswordsInfo *info, gboolean retry)
 		}
 
 		if (save) {
-			if (info->password) {
-				keyring_helpers_save_secret (info->vpn_uuid, info->vpn_name,
-											 keyring, NM_OPENVPN_KEY_PASSWORD, info->password);
+			if (*out_password) {
+				keyring_helpers_save_secret (vpn_uuid, vpn_name, keyring,
+											 NM_OPENVPN_KEY_PASSWORD, *out_password);
 			}
-			if (info->certpass) {
-				keyring_helpers_save_secret (info->vpn_uuid, info->vpn_name,
-											 keyring, NM_OPENVPN_KEY_CERTPASS, info->certpass);
+			if (*out_certpass) {
+				keyring_helpers_save_secret (vpn_uuid, vpn_name, keyring,
+											 NM_OPENVPN_KEY_CERTPASS, *out_certpass);
 			}
 		}
 
@@ -179,117 +183,71 @@ get_secrets (PasswordsInfo *info, gboolean retry)
 	return success;
 }
 
-static gboolean
-get_password_types (PasswordsInfo *info)
+static void
+get_password_types (GHashTable *data,
+                    gboolean *out_need_password,
+                    gboolean *out_need_certpass)
 {
-	GConfClient *gconf_client = NULL;
-	GSList *conf_list;
-	GSList *iter;
-	char *key;
-	char *str;
-	char *connection_path = NULL;
-	gboolean success = FALSE;
-	char *connection_type;
-
-	/* FIXME: This whole thing sucks: we should not go around poking gconf
-	   directly, but there's nothing that does it for us right now */
-
-	gconf_client = gconf_client_get_default ();
-
-	conf_list = gconf_client_all_dirs (gconf_client, "/system/networking/connections", NULL);
-	if (!conf_list)
-		return FALSE;
-
-	for (iter = conf_list; iter; iter = iter->next) {
-		const char *path = (const char *) iter->data;
-
-		key = g_strdup_printf ("%s/%s/%s", 
-		                       path,
-		                       NM_SETTING_CONNECTION_SETTING_NAME,
-		                       NM_SETTING_CONNECTION_TYPE);
-		str = gconf_client_get_string (gconf_client, key, NULL);
-		g_free (key);
-
-		if (!str || strcmp (str, "vpn")) {
-			g_free (str);
-			continue;
-		}
-		g_free (str);
-
-		key = g_strdup_printf ("%s/%s/%s", 
-		                       path,
-		                       NM_SETTING_CONNECTION_SETTING_NAME,
-		                       NM_SETTING_CONNECTION_UUID);
-		str = gconf_client_get_string (gconf_client, key, NULL);
-		g_free (key);
-
-		if (!str || strcmp (str, info->vpn_uuid)) {
-			g_free (str);
-			continue;
-		}
-		g_free (str);
-
-		/* Woo, found the connection */
-		connection_path = g_strdup (path);
-		break;
-	}
-
-	g_slist_foreach (conf_list, (GFunc) g_free, NULL);
-	g_slist_free (conf_list);
-
-	if (!connection_path)
-		goto out;
-
-	key = g_strdup_printf ("%s/%s/%s", connection_path,
-	                       NM_SETTING_VPN_SETTING_NAME,
-	                       NM_OPENVPN_KEY_CONNECTION_TYPE);
-	connection_type = gconf_client_get_string (gconf_client, key, NULL);
-	g_free (key);
-	
-	if (   !strcmp (connection_type, NM_OPENVPN_CONTYPE_TLS)
-	    || !strcmp (connection_type, NM_OPENVPN_CONTYPE_PASSWORD_TLS)) {
-		success = TRUE;
-
-		if (!strcmp (connection_type, NM_OPENVPN_CONTYPE_PASSWORD_TLS))
-			info->need_password = TRUE;
-
-		key = g_strdup_printf ("%s/%s/%s", connection_path, NM_SETTING_VPN_SETTING_NAME,
-		                       NM_OPENVPN_KEY_KEY);
-		str = gconf_client_get_string (gconf_client, key, NULL);
-		info->need_certpass = is_encrypted (str);
-		g_free (str);
-		g_free (key);
-	} else if (!strcmp (connection_type, NM_OPENVPN_CONTYPE_STATIC_KEY)) {
-		success = TRUE;
-	} else if (!strcmp (connection_type, NM_OPENVPN_CONTYPE_PASSWORD)) {
-		success = TRUE;
-		info->need_password = TRUE;
+	const char *ctype, *val;
+
+	ctype = g_hash_table_lookup (data, NM_OPENVPN_KEY_CONNECTION_TYPE);
+	if (ctype) {
+		if (!strcmp (ctype, NM_OPENVPN_CONTYPE_TLS) || !strcmp (ctype, NM_OPENVPN_CONTYPE_PASSWORD_TLS)) {
+			/* Normal user password */
+			if (!strcmp (ctype, NM_OPENVPN_CONTYPE_PASSWORD_TLS))
+				*out_need_password = TRUE;
+
+			/* Encrypted private key password */
+			val = g_hash_table_lookup (data, NM_OPENVPN_KEY_KEY);
+			if (val)
+				*out_need_certpass = is_encrypted (val);
+		} else if (!strcmp (ctype, NM_OPENVPN_CONTYPE_PASSWORD))
+			*out_need_password = TRUE;
 	}
+}
 
-	g_free (connection_type);
-	g_free (connection_path);
-
-out:
-	g_object_unref (gconf_client);
-	return success;
+static void
+wait_for_quit (void)
+{
+	GString *str;
+	char c;
+	ssize_t n;
+	time_t start;
+
+	str = g_string_sized_new (10);
+	start = time (NULL);
+	do {
+		errno = 0;
+		n = read (0, &c, 1);
+		if (n == 0 || (n < 0 && errno == EAGAIN))
+			g_usleep (G_USEC_PER_SEC / 10);
+		else if (n == 1) {
+			g_string_append_c (str, c);
+			if (strstr (str->str, "QUIT") || (str->len > 10))
+				break;
+		} else
+			break;
+	} while (time (NULL) < start + 20);
+	g_string_free (str, TRUE);
 }
 
 int 
 main (int argc, char *argv[])
 {
-	PasswordsInfo info;
-	gboolean retry = FALSE;
+	gboolean retry = FALSE, allow_interaction = FALSE;
 	gchar *vpn_name = NULL;
 	gchar *vpn_uuid = NULL;
 	gchar *vpn_service = NULL;
-	char buf[1];
-	int ret;
+	GHashTable *data = NULL, *secrets = NULL;
+	gboolean need_password = FALSE, need_certpass = FALSE;
+	char *new_password = NULL, *new_certpass = NULL;
 	GOptionContext *context;
 	GOptionEntry entries[] = {
 			{ "reprompt", 'r', 0, G_OPTION_ARG_NONE, &retry, "Reprompt for passwords", NULL},
 			{ "uuid", 'u', 0, G_OPTION_ARG_STRING, &vpn_uuid, "UUID of VPN connection", NULL},
 			{ "name", 'n', 0, G_OPTION_ARG_STRING, &vpn_name, "Name of VPN connection", NULL},
 			{ "service", 's', 0, G_OPTION_ARG_STRING, &vpn_service, "VPN service type", NULL},
+			{ "allow-interaction", 'i', 0, G_OPTION_ARG_NONE, &allow_interaction, "Allow user interaction", NULL},
 			{ NULL }
 		};
 
@@ -314,36 +272,54 @@ main (int argc, char *argv[])
 		return EXIT_FAILURE;
 	}
 
-	memset (&info, 0, sizeof (PasswordsInfo));
-	info.vpn_uuid = vpn_uuid;
-	info.vpn_name = vpn_name;
-
-	if (!get_password_types (&info)) {
-		fprintf (stderr, "Invalid connection");
-		return EXIT_FAILURE;
+	if (!nm_vpn_plugin_utils_read_vpn_details (0, &data, &secrets)) {
+		fprintf (stderr, "Failed to read '%s' (%s) data and secrets from stdin.\n",
+		         vpn_name, vpn_uuid);
+		return 1;
 	}
 
-	if (!info.need_password && !info.need_certpass) {
+	get_password_types (data, &need_password, &need_certpass);
+
+	if (!need_password && !need_certpass) {
 		printf ("%s\n%s\n\n\n", NM_OPENVPN_KEY_NOSECRET, "true");
-		return EXIT_SUCCESS;
+		return 0;
 	}
 
-	if (get_secrets (&info, retry)) {
-		if (info.need_password)
-			printf ("%s\n%s\n", NM_OPENVPN_KEY_PASSWORD, info.password);
-		if (info.need_certpass)
-			printf ("%s\n%s\n", NM_OPENVPN_KEY_CERTPASS, info.certpass);
+	if (get_secrets (vpn_name,
+	                 vpn_uuid,
+	                 need_password,
+	                 need_certpass,
+	                 retry,
+	                 allow_interaction,
+	                 g_hash_table_lookup (secrets, NM_OPENVPN_KEY_PASSWORD),
+	                 &new_password,
+	                 g_hash_table_lookup (secrets, NM_OPENVPN_KEY_CERTPASS),
+	                 &new_certpass)) {
+		if (need_password)
+			printf ("%s\n%s\n", NM_OPENVPN_KEY_PASSWORD, new_password);
+		if (need_certpass)
+			printf ("%s\n%s\n", NM_OPENVPN_KEY_CERTPASS, new_certpass);
 	}
 	printf ("\n\n");
 
-	clear_secrets (&info);
+	if (new_password) {
+		memset (new_password, 0, strlen (new_password));
+		gnome_keyring_memory_free (new_password);
+	}
+	if (new_certpass) {
+		memset (new_certpass, 0, strlen (new_certpass));
+		gnome_keyring_memory_free (new_certpass);
+	}
 
 	/* for good measure, flush stdout since Kansas is going Bye-Bye */
 	fflush (stdout);
 
-	/* wait for data on stdin  */
-	ret = fread (buf, sizeof (char), sizeof (buf), stdin);
-
+	/* Wait for quit signal */
+	wait_for_quit ();
 
-	return EXIT_SUCCESS;
+	if (data)
+		g_hash_table_unref (data);
+	if (secrets)
+		g_hash_table_unref (secrets);
+	return 0;
 }



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]