NetworkManager r3309 - in trunk: . system-settings/plugins/ifcfg-fedora system-settings/src



Author: dcbw
Date: Tue Feb 12 19:20:18 2008
New Revision: 3309
URL: http://svn.gnome.org/viewvc/NetworkManager?rev=3309&view=rev

Log:
2008-02-12  Dan Williams  <dcbw redhat com>

	* system-settings/src/nm-system-config-interface.c
	  system-settings/src/nm-system-config-interface.h
		- (load_connections): get_connections() should now return an allocated
			GSList that the system settings service will free

	* system-settings/plugins/ifcfg-fedora/plugin.c
	  system-settings/plugins/ifcfg-fedora/parser.h
	  system-settings/plugins/ifcfg-fedora/parser.c
		- Fix up inotify issues; handle keys-* files, handle new files appearing
			in the profile directory, handle resolv.conf file changes




Modified:
   trunk/ChangeLog
   trunk/system-settings/plugins/ifcfg-fedora/parser.c
   trunk/system-settings/plugins/ifcfg-fedora/parser.h
   trunk/system-settings/plugins/ifcfg-fedora/plugin.c
   trunk/system-settings/src/main.c
   trunk/system-settings/src/nm-system-config-interface.h

Modified: trunk/system-settings/plugins/ifcfg-fedora/parser.c
==============================================================================
--- trunk/system-settings/plugins/ifcfg-fedora/parser.c	(original)
+++ trunk/system-settings/plugins/ifcfg-fedora/parser.c	Tue Feb 12 19:20:18 2008
@@ -184,29 +184,23 @@
 #define SEARCH_TAG "search "
 #define NS_TAG "nameserver "
 
-static void
-read_profile_resolv_conf (shvarFile *ifcfg, NMSettingIP4Config *s_ip4)
+void
+connection_update_from_resolv_conf (char **lines, NMSettingIP4Config *s_ip4)
 {
-	char *file = NULL;
-	char *dir = NULL;
-	char *contents = NULL;
-	char **lines = NULL;
 	char **line;
 
-	dir = g_path_get_dirname (ifcfg->fileName);
-	if (!dir)
-		goto out;
-
-	file = g_strdup_printf ("%s/resolv.conf", dir);
-	if (!file)
-		goto out;
-
-	if (!g_file_get_contents (file, &contents, NULL, NULL))
-		goto out;
+	/* lines == NULL means clear out existing settings */
+	if (!lines) {
+		if (s_ip4->dns) {
+			g_array_free (s_ip4->dns, TRUE);
+			s_ip4->dns = NULL;
+		}
 
-	lines = g_strsplit (contents, "\n", 0);
-	if (!lines || !*lines)
-		goto out;
+		g_slist_foreach (s_ip4->dns_search, (GFunc) g_free, NULL);
+		g_slist_free (s_ip4->dns_search);
+		s_ip4->dns_search = NULL;
+		return;
+	}
 
 	s_ip4->dns = g_array_new (FALSE, FALSE, sizeof (guint32));
 
@@ -237,9 +231,36 @@
 		}
 	}
 
+	if (!s_ip4->dns->len) {
+		g_array_free (s_ip4->dns, TRUE);
+		s_ip4->dns = NULL;
+	}
+}
+
+static void
+read_profile_resolv_conf (const char *dir, NMSettingIP4Config *s_ip4)
+{
+	char *file = NULL;
+	char *contents = NULL;
+	char **lines = NULL;
+
+	file = g_strdup_printf ("%s/resolv.conf", dir);
+	if (!file)
+		goto out;
+
+	if (!g_file_get_contents (file, &contents, NULL, NULL))
+		goto out;
+
+	lines = g_strsplit (contents, "\n", 0);
+	if (!lines || !*lines)
+		goto out;
+
+	connection_update_from_resolv_conf (lines, s_ip4);
+
 out:
 	if (lines)
 		g_strfreev (lines);
+	g_free (contents);
 	g_free (file);
 }
 
@@ -250,6 +271,7 @@
 	char *value = NULL;
 	NMSettingIP4Address tmp = { 0, 0, 0 };
 	gboolean manual = TRUE;
+	char *dir;
 
 	value = svGetValue (ifcfg, "BOOTPROTO");
 	if (!value)
@@ -308,7 +330,15 @@
 		s_ip4->addresses = g_slist_append (s_ip4->addresses, addr);
 	}
 
-	read_profile_resolv_conf (ifcfg, s_ip4);
+	dir = g_path_get_dirname (ifcfg->fileName);
+	if (dir) {
+		read_profile_resolv_conf (dir, s_ip4);
+		g_free (dir);
+	} else {
+		g_set_error (error, ifcfg_plugin_error_quark (), 0,
+		             "Not enough memory to parse resolv.conf");
+		goto error;
+	}
 
 	return NM_SETTING (s_ip4);
 
@@ -433,7 +463,7 @@
 	if (!tmp)
 		goto out;
 
-	keys_file = g_strdup_printf ("%s/keys-%s", tmp, ifcfg_name);
+	keys_file = g_strdup_printf ("%s/" KEYS_TAG "%s", tmp, ifcfg_name);
 	if (!keys_file)
 		goto out;
 
@@ -746,6 +776,8 @@
 	char *nmc = NULL;
 	NMSetting *s_ip4;
 	char *ifcfg_name = NULL;
+	gboolean ignored = FALSE;
+	ConnectionData *cdata;
 
 	g_return_val_if_fail (file != NULL, NULL);
 
@@ -778,12 +810,8 @@
 		lower = g_ascii_strdown (nmc, -1);
 		g_free (nmc);
 
-		if (!strcmp (lower, "no") || !strcmp (lower, "n") || !strcmp (lower, "false")) {
-			g_free (lower);
-			g_set_error (error, ifcfg_plugin_error_quark (), 0,
-			             "Ignoring connection '%s' because NM_CONTROLLED was false.", file);
-			goto done;
-		}
+		if (!strcmp (lower, "no") || !strcmp (lower, "n") || !strcmp (lower, "false"))
+			ignored = TRUE;
 		g_free (lower);
 	}
 
@@ -810,6 +838,10 @@
 		nm_connection_add_setting (connection, s_ip4);
 	}
 
+	/* Update the ignored tag */
+	cdata = connection_data_get (connection);
+	cdata->ignored = ignored;
+
 	if (!nm_connection_verify (connection)) {
 		g_object_unref (connection);
 		connection = NULL;

Modified: trunk/system-settings/plugins/ifcfg-fedora/parser.h
==============================================================================
--- trunk/system-settings/plugins/ifcfg-fedora/parser.h	(original)
+++ trunk/system-settings/plugins/ifcfg-fedora/parser.h	Tue Feb 12 19:20:18 2008
@@ -24,17 +24,24 @@
 
 #include <glib.h>
 #include <nm-connection.h>
+#include <nm-setting-ip4-config.h>
 
 #define IFCFG_TAG "ifcfg-"
+#define KEYS_TAG "keys-"
 #define BAK_TAG ".bak"
 
 typedef struct {
 	char *ifcfg_path;
+	gboolean ignored;
+	gboolean exported;
+
 	GHashTable *secrets;
 } ConnectionData;
 
 NMConnection * parser_parse_file (const char *file, GError **error);
 
+void connection_update_from_resolv_conf (char **lines, NMSettingIP4Config *s_ip4);
+
 ConnectionData *connection_data_get (NMConnection *connection);
 ConnectionData *connection_data_add (NMConnection *connection, const char *ifcfg_path);
 void connection_data_copy_secrets (ConnectionData *from, ConnectionData *to);

Modified: trunk/system-settings/plugins/ifcfg-fedora/plugin.c
==============================================================================
--- trunk/system-settings/plugins/ifcfg-fedora/plugin.c	(original)
+++ trunk/system-settings/plugins/ifcfg-fedora/plugin.c	Tue Feb 12 19:20:18 2008
@@ -111,61 +111,87 @@
 static void
 watch_path (const char *path, const int inotify_fd, GHashTable *table)
 {
-	char *dirname;
 	int wd;
 	struct FindInfo info;
 
-	dirname = g_path_get_dirname (path);
-	g_return_if_fail (dirname != NULL);
+	g_return_if_fail (g_path_is_absolute (path));
 
 	info.found = FALSE;
-	info.path = dirname;
+	info.path = path;
 	g_hash_table_foreach (table, find_watched_path, &info);
 	if (info.found)
-		goto error;
+		return;
 
-	wd = inotify_add_watch (inotify_fd, dirname,
-	                        IN_CLOSE_WRITE | IN_CREATE | IN_DELETE | IN_MOVE);
+	wd = inotify_add_watch (inotify_fd, path,
+	                        IN_CLOSE_WRITE | IN_CREATE | IN_DELETE | IN_MOVE | IN_MOVE_SELF);
 	if (wd == -1) {
 		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "    inotify error watching '%s': errno %d",
-		              dirname, errno);
-		goto error;
+		              path, errno);
+	} else {
+		g_hash_table_insert (table, GINT_TO_POINTER (wd), g_strdup (path));
 	}
-
-	g_hash_table_insert (table, GINT_TO_POINTER (wd), dirname);
-	return;
-
-error:
-	g_free (dirname);
 }
 
 static NMConnection *
 build_one_connection (const char *profile_path, const char *filename)
 {
 	NMConnection *connection;
-	char *ifcfg_file = NULL;
 	GError *error = NULL;
 
 	g_return_val_if_fail (profile_path != NULL, NULL);
 	g_return_val_if_fail (filename != NULL, NULL);
 
-	ifcfg_file = g_build_filename (profile_path, filename, NULL);
-	g_return_val_if_fail (ifcfg_file != NULL, NULL);
+	PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "parsing %s ... ", filename);
 
-	PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "parsing %s ... ", ifcfg_file);
-
-	connection = parser_parse_file (ifcfg_file, &error);
+	connection = parser_parse_file (filename, &error);
 	if (connection) {
 		NMSettingConnection *s_con;
 
 		s_con = NM_SETTING_CONNECTION (nm_connection_get_setting (connection, NM_TYPE_SETTING_CONNECTION));
 		g_assert (s_con);
 		g_assert (s_con->id);
-		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "    found connection '%s'", s_con->id);
+		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "    read connection '%s'", s_con->id);
 	} else {
 		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "    error: %s",
 		              error->message ? error->message : "(unknown)");
-		g_free (ifcfg_file);
+	}
+
+	return connection;
+}
+
+static NMConnection *
+handle_new_ifcfg (const char *profile_path,
+                  const char *file,
+                  const int inotify_fd,
+                  GHashTable *watch_table)
+{
+	NMConnection *connection;
+	ConnectionData *cdata;
+	char *keys_file, *basename;
+
+	connection = build_one_connection (profile_path, file);
+	if (!connection)
+		return NULL;
+
+	/* Watch the file too so we can match up the watch descriptor with the
+	 * path we care about if the file is a hardlink.
+	 */
+	watch_path (file, inotify_fd, watch_table);
+
+	/* If there's a keys file watch that too */
+	basename = g_path_get_basename (file);
+	if (basename) {
+		keys_file = g_strdup_printf ("%s" KEYS_TAG "%s", profile_path, basename + strlen (IFCFG_TAG));
+		if (keys_file && g_file_test (keys_file, G_FILE_TEST_EXISTS))
+			watch_path (keys_file, inotify_fd, watch_table);
+		g_free (keys_file);
+		g_free (basename);
+	}
+
+	cdata = connection_data_get (connection);
+	if (cdata->ignored) {
+		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "Ignoring connection '%s' because "
+		              "NM_CONTROLLED was false.", file);
 	}
 
 	return connection;
@@ -179,6 +205,7 @@
 	GSList *connections = NULL;
 	GDir *dir;
 	const char *item;
+	char *resolv_conf;
 
 	g_return_val_if_fail (profile_path != NULL, NULL);
 	g_return_val_if_fail (watch_table != NULL, NULL);
@@ -191,17 +218,29 @@
 
 	while ((item = g_dir_read_name (dir))) {
 		NMConnection *connection;
+		char *ifcfg_file;
 
 		if (strncmp (item, IFCFG_TAG, strlen (IFCFG_TAG)))
 			continue;
 
-		connection = build_one_connection (profile_path, item);
+		ifcfg_file = g_build_filename (profile_path, item, NULL);
+
+		connection = handle_new_ifcfg (profile_path, ifcfg_file, inotify_fd, watch_table);
 		if (connection)
 			connections = g_slist_append (connections, connection);
+
+		g_free (ifcfg_file);
 	}
 	g_dir_close (dir);
 
 	watch_path (profile_path, inotify_fd, watch_table);
+
+	/* Watch resolv.conf too */
+	resolv_conf = g_strdup_printf ("%sresolv.conf", profile_path);
+	if (g_file_test (resolv_conf, G_FILE_TEST_EXISTS))
+		watch_path (resolv_conf, inotify_fd, watch_table);
+	g_free (resolv_conf);
+
 	return connections;
 }
 
@@ -262,11 +301,23 @@
 {
 	SCPluginIfcfg *plugin = SC_PLUGIN_IFCFG (config);
 	SCPluginIfcfgPrivate *priv = SC_PLUGIN_IFCFG_GET_PRIVATE (plugin);
+	GSList *list = NULL, *iter;
 
 	if (!priv->initialized)
 		reload_all_connections (plugin);
 
-	return priv->connections;
+	for (iter = priv->connections; iter; iter = g_slist_next (iter)) {
+		NMConnection *connection = NM_CONNECTION (iter->data);
+		ConnectionData *cdata;
+
+		cdata = connection_data_get (connection);
+		if (!cdata->ignored) {
+			list = g_slist_append (list, connection);
+			cdata->exported = TRUE;
+		}
+	}
+
+	return list;
 }
 
 static GHashTable *
@@ -308,67 +359,200 @@
 }
 
 static void
-handle_profile_item_changed (SCPluginIfcfg *plugin,
-                             struct inotify_event *evt,
-                             const char *filename)
+handle_connection_changed (SCPluginIfcfg *plugin,
+                           const char *filename)
 {
 	SCPluginIfcfgPrivate *priv = SC_PLUGIN_IFCFG_GET_PRIVATE (plugin);
-	const char *path;
+	NMConnection *new_connection;
+	NMConnection *existing;
+	ConnectionData *new_cdata;
+	GHashTable *new_settings;
+	ConnectionData *existing_cdata;
+	gboolean remove = FALSE;
+
+	/* Could return NULL if the connection got deleted */
+	new_connection = build_one_connection (priv->profile, filename);
+
+	existing = find_connection_by_path (priv->connections, filename);
+	if (!existing) {
+		if (new_connection) {
+			new_cdata = connection_data_get (new_connection);
+			g_assert (new_cdata);
 
-	g_return_if_fail (plugin != NULL);
-	g_return_if_fail (evt != NULL);
-
-	path = g_hash_table_lookup (priv->watch_table, GINT_TO_POINTER (evt->wd));
-	if (!path)
+			/* totally new connection */
+			priv->connections = g_slist_append (priv->connections, new_connection);
+			if (!new_cdata->ignored) {
+				new_cdata->exported = TRUE;
+				g_signal_emit_by_name (plugin, "connection-added", new_connection);
+			}
+		}
 		return;
+	}
 
-	if (!strncmp (filename, IFCFG_TAG, strlen (IFCFG_TAG))) {
-		NMConnection *new_connection;
-		NMConnection *existing;
-		ConnectionData *new_cdata;
-
-		new_connection = build_one_connection (priv->profile, filename);
-		if (!new_connection)
-			goto out;
-
-		new_cdata = connection_data_get (new_connection);
-		g_assert (new_cdata);
-
-		existing = find_connection_by_path (priv->connections, new_cdata->ifcfg_path);
-		if (existing) {
-			GHashTable *new_settings;
-			ConnectionData *existing_cdata;
+	existing_cdata = connection_data_get (existing);
+	g_assert (existing_cdata);
 
-			/* update the settings of the existing connection for this
-			 * ifcfg file and notify listeners that something has changed.
+	if (new_connection) {
+		/* update the settings of the existing connection for this
+		 * ifcfg file and notify listeners that something has changed.
+		 */
+		new_settings = nm_connection_to_hash (new_connection);
+		if (!nm_connection_replace_settings (existing, new_settings)) {
+			/* couldn't replace the settings for some reason; have to
+			 * remove the connection then.
 			 */
-			new_settings = nm_connection_to_hash (new_connection);
-			if (!nm_connection_replace_settings (existing, new_settings)) {
-				/* couldn't replace the settings for some reason; have to
-				 * remove the connection then.
-				 */
-				PLUGIN_WARN (IFCFG_PLUGIN_NAME, "couldn't update connection for '%s'.", filename);
-				priv->connections = g_slist_remove (priv->connections, existing);
+			PLUGIN_WARN (IFCFG_PLUGIN_NAME, "couldn't update connection for '%s'.", filename);
+			remove = TRUE;
+		} else {
+			/* Success */
+			new_cdata = connection_data_get (new_connection);
+			g_assert (new_cdata);
+
+			connection_data_copy_secrets (new_cdata, existing_cdata);
+
+			if (new_cdata->ignored && !existing_cdata->ignored) {
+				/* connection now ignored */
+				existing_cdata->ignored = TRUE;
 				g_signal_emit_by_name (plugin, "connection-removed", existing);
-				g_object_unref (existing);
-			} else {
-				existing_cdata = connection_data_get (existing);
-				g_assert (existing_cdata);
-				connection_data_copy_secrets (new_cdata, existing_cdata);
+				existing_cdata->exported = FALSE;
+			} else if (!new_cdata->ignored && existing_cdata->ignored) {
+				/* connection no longer ignored, let the system settings
+				 * service know about it now.
+				 */
+				existing_cdata->ignored = FALSE;
+				existing_cdata->exported = TRUE;
+				g_signal_emit_by_name (plugin, "connection-added", existing);
+			} else if (!new_cdata->ignored && !existing_cdata->ignored) {
+				/* connection updated and not ignored */
 				g_signal_emit_by_name (plugin, "connection-updated", existing);
+			} else if (new_cdata->ignored && existing_cdata->ignored) {
+				/* do nothing */
 			}
-			g_object_unref (new_connection);
-		} else {
-			/* totally new connection */
-			priv->connections = g_slist_append (priv->connections, new_connection);
-			g_signal_emit_by_name (plugin, "connection-added", new_connection);
 		}
-	} else if (!strcmp (filename, "resolv.conf")) {
-		// Update dns entries in all connections
+		g_object_unref (new_connection);
+	} else {
+		remove = TRUE;
 	}
 
-out:
-	return;
+	if (remove) {
+		priv->connections = g_slist_remove (priv->connections, existing);
+		if (!existing_cdata->ignored)
+			g_signal_emit_by_name (plugin, "connection-removed", existing);
+		g_object_unref (existing);
+	}
+}
+
+static void
+handle_resolv_conf_changed (SCPluginIfcfg *plugin, const char *path)
+{
+	SCPluginIfcfgPrivate *priv = SC_PLUGIN_IFCFG_GET_PRIVATE (plugin);
+	char *contents = NULL;
+	char **lines = NULL;
+	GSList *iter;
+
+	g_return_if_fail (path != NULL);
+
+	g_file_get_contents (path, &contents, NULL, NULL);
+	if (contents) {
+		lines = g_strsplit (contents, "\n", 0);
+		if (lines && !*lines) {
+			g_strfreev (lines);
+			lines = NULL;
+		}
+	}
+
+	if (lines) {
+		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "Updating connections because %s changed.", path);
+	} else {
+		PLUGIN_PRINT (IFCFG_PLUGIN_NAME, "Updating connections because %s was deleted.", path);
+	}
+
+	for (iter = priv->connections; iter; iter = g_slist_next (iter)) {
+		NMConnection *connection = NM_CONNECTION (iter->data);
+		NMSettingIP4Config *s_ip4;
+
+		s_ip4 = NM_SETTING_IP4_CONFIG (nm_connection_get_setting (connection, NM_TYPE_SETTING_IP4_CONFIG));
+		if (s_ip4) {
+			ConnectionData *cdata;
+
+			cdata = connection_data_get (connection);
+			g_assert (cdata);
+
+			connection_update_from_resolv_conf (lines, s_ip4);
+
+			if (!cdata->ignored)
+				g_signal_emit_by_name (plugin, "connection-updated", connection);
+		}
+	}
+
+	if (lines)
+		g_strfreev (lines);
+	g_free (contents);
+}
+
+static void
+handle_profile_item_changed (SCPluginIfcfg *plugin, const char *path)
+{
+	SCPluginIfcfgPrivate *priv = SC_PLUGIN_IFCFG_GET_PRIVATE (plugin);
+	char *basename;
+
+	g_return_if_fail (plugin != NULL);
+	g_return_if_fail (path != NULL);
+
+	basename = g_path_get_basename (path);
+	if (!basename) {
+		PLUGIN_WARN (IFCFG_PLUGIN_NAME, "not enough memory to parse connection change.");
+		return;
+	}
+
+	if (!strncmp (basename, IFCFG_TAG, strlen (IFCFG_TAG)))
+		handle_connection_changed (plugin, path);
+	else if (!strncmp (basename, KEYS_TAG, strlen (KEYS_TAG))) {
+		char *ifcfg;
+		
+		ifcfg = g_strdup_printf ("%s" IFCFG_TAG "%s", priv->profile, basename + strlen (KEYS_TAG));
+		if (ifcfg)
+			handle_connection_changed (plugin, ifcfg);
+		g_free (ifcfg);
+	} else if (!strcmp (basename, "resolv.conf"))
+		handle_resolv_conf_changed (plugin, path);
+
+	g_free (basename);
+}
+
+static void
+handle_profile_item_new (SCPluginIfcfg *plugin, const char *filename)
+{
+	SCPluginIfcfgPrivate *priv = SC_PLUGIN_IFCFG_GET_PRIVATE (plugin);
+	char *path;
+
+	path = g_strdup_printf ("%s%s", priv->profile, filename);
+	if (!path)
+		return;
+
+	if (!strcmp (filename, "resolv.conf")) {
+		watch_path (path, priv->ifd, priv->watch_table);
+		handle_resolv_conf_changed (plugin, path);
+	} else if (!strncmp (filename, IFCFG_TAG, strlen (IFCFG_TAG))) {
+		NMConnection *connection;
+
+		connection = handle_new_ifcfg (priv->profile, path, priv->ifd, priv->watch_table);
+		if (connection) {
+			ConnectionData *cdata;
+
+			cdata = connection_data_get (connection);
+			g_assert (cdata);
+
+			/* new connection */
+			priv->connections = g_slist_append (priv->connections, connection);
+			if (!cdata->ignored) {
+				cdata->exported = TRUE;
+				g_signal_emit_by_name (plugin, "connection-added", connection);
+			}
+		}
+	}
+
+	g_free (path);
 }
 
 static gboolean
@@ -380,18 +564,30 @@
 
 	/* read the notifications from the watch descriptor */
 	while (g_io_channel_read_chars (channel, (gchar *) &evt, sizeof (struct inotify_event), NULL, NULL) == G_IO_STATUS_NORMAL) {
+		const char *path;
 		gchar filename[PATH_MAX + 1];
 
-		if (evt.len <= 0)
-			continue;
+		path = g_hash_table_lookup (priv->watch_table, GINT_TO_POINTER (evt.wd));
 
-		g_io_channel_read_chars (channel,
-		                         filename,
-		                         evt.len > PATH_MAX ? PATH_MAX : evt.len,
-		                         NULL, NULL);
+		filename[0] = '\0';
+		if (evt.len > 0) {
+			g_io_channel_read_chars (channel,
+			                        filename,
+			                        evt.len > PATH_MAX ? PATH_MAX : evt.len,
+			                        NULL, NULL);
+		}
+
+		if (!path && !strlen (filename)) {
+			PLUGIN_WARN (IFCFG_PLUGIN_NAME, "unhandled inotify event.");
+			continue;
+		}
 
 		if (evt.wd == priv->profile_wd) {
-			if (!strcmp (filename, "network")) {
+			char *basename;
+
+			basename = g_path_get_basename (filename);
+
+			if (basename && !strcmp (basename, "network")) {
 				char *new_profile;
 
 				new_profile = get_current_profile_path ();
@@ -406,8 +602,21 @@
 				}
 				g_free (new_profile);
 			}
-		} else
-			handle_profile_item_changed (plugin, &evt, filename);
+			g_free (basename);
+		} else {
+			/* If the item was deleted, stop tracking its watch */
+			if (evt.mask & (IN_DELETE | IN_DELETE_SELF)) {
+				inotify_rm_watch (priv->ifd, evt.wd);
+				g_hash_table_remove (priv->watch_table, GINT_TO_POINTER (evt.wd));
+			}
+
+			if (strlen (filename) && !strcmp (path, priv->profile)) {
+				/* Some file appeared */
+				handle_profile_item_new (plugin, filename);
+			} else {
+				handle_profile_item_changed (plugin, path);
+			}
+		}
 	}
 
 	return TRUE;

Modified: trunk/system-settings/src/main.c
==============================================================================
--- trunk/system-settings/src/main.c	(original)
+++ trunk/system-settings/src/main.c	Tue Feb 12 19:20:18 2008
@@ -261,6 +261,8 @@
 			g_object_set_data (G_OBJECT (elt->data), NM_SS_PLUGIN_TAG, plugin);
 			connection_added_cb (NM_SYSTEM_CONFIG_INTERFACE (plugin), NM_CONNECTION (elt->data), app);
 		}
+
+		g_slist_free (plugin_connections);
 	}
 
 	return FALSE;

Modified: trunk/system-settings/src/nm-system-config-interface.h
==============================================================================
--- trunk/system-settings/src/nm-system-config-interface.h	(original)
+++ trunk/system-settings/src/nm-system-config-interface.h	Tue Feb 12 19:20:18 2008
@@ -75,7 +75,7 @@
 	void     (*init) (NMSystemConfigInterface *config);
 
 	/* Returns the plugins currently known list of connections.  The returned
-	 * list is owned by the plugin and not freed by the system settings service.
+	 * list is freed by the system settings service.
 	 */
 	GSList * (*get_connections) (NMSystemConfigInterface *config);
 



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