changeset 21199:fb8f9bf86315

* Add purple_plugin_disable() to prevent plugins from loading on the next startup. A UI would call this when purple_plugin_unload() returns FALSE. * Make purple_plugin_unload() set plugin->error instead of popping up a notification if a dependent plugin can't be unloaded.
author Richard Laager <rlaager@wiktel.com>
date Sun, 07 Oct 2007 16:02:55 +0000
parents b6136fd465a0
children 31821456d93f
files ChangeLog.API libpurple/plugin.c libpurple/plugin.h
diffstat 3 files changed, 46 insertions(+), 20 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog.API	Sun Oct 07 15:58:57 2007 +0000
+++ b/ChangeLog.API	Sun Oct 07 16:02:55 2007 +0000
@@ -12,6 +12,9 @@
 		Changed:
 		* purple_plugin_unload() now honors the return value of a
 		  plugin's unload function and can actually return FALSE now.
+		* purple_plugin_unload() no longer does its own notifications
+		  when a dependent plugin fails to unload.  The UI should do
+		  something appropriate.
 
 version 2.2.0 (09/13/2007):
 	libpurple:
--- a/libpurple/plugin.c	Sun Oct 07 15:58:57 2007 +0000
+++ b/libpurple/plugin.c	Sun Oct 07 16:02:55 2007 +0000
@@ -58,6 +58,7 @@
 #ifdef PURPLE_PLUGINS
 static GList *load_queue       = NULL;
 static GList *plugin_loaders   = NULL;
+static GList *plugins_to_disable = NULL;
 #endif
 
 static void (*probe_cb)(void *) = NULL;
@@ -658,15 +659,10 @@
 		{
 			if (!purple_plugin_unload(dep_plugin))
 			{
-				char *tmp;
-
-				tmp = g_strdup_printf(_("The dependent plugin %s failed to unload."),
-				                      _(dep_plugin->info->name));
-
-				purple_notify_error(NULL, NULL,
-				                    _("There were errors unloading the plugin."), tmp);
-				g_free(tmp);
-
+				g_free(plugin->error);
+				plugin->error = g_strdup_printf(_("%s requires %s, but it failed to unload."),
+				                                _(plugin->info->name),
+				                                _(dep_plugin->info->name));
 				return FALSE;
 			}
 			else
@@ -691,9 +687,8 @@
 	}
 
 	if (plugin->native_plugin) {
-		if (plugin->info->unload != NULL)
-			if (!plugin->info->unload(plugin))
-				return FALSE;
+		if (plugin->info->unload && !plugin->info->unload(plugin))
+			return FALSE;
 
 		if (plugin->info->type == PURPLE_PLUGIN_PROTOCOL) {
 			PurplePluginProtocolInfo *prpl_info;
@@ -728,9 +723,8 @@
 
 		loader_info = PURPLE_PLUGIN_LOADER_INFO(loader);
 
-		if (loader_info->unload != NULL)
-			if (!loader_info->unload(plugin))
-				return FALSE;
+		if (loader_info->unload && !loader_info->unload(plugin))
+			return FALSE;
 	}
 
 	/* cancel any pending dialogs the plugin has */
@@ -743,8 +737,16 @@
 	loaded_plugins = g_list_remove(loaded_plugins, plugin);
 	if ((plugin->info != NULL) && PURPLE_IS_PROTOCOL_PLUGIN(plugin))
 		protocol_plugins = g_list_remove(protocol_plugins, plugin);
+	plugins_to_disable = g_list_remove(plugins_to_disable, plugin);
 	plugin->loaded = FALSE;
 
+	/* We wouldn't be anywhere near here if the plugin wasn't loaded, so
+	 * if plugin->error is set at all, it had to be from a previous
+	 * unload failure.  It's obviously okay now.
+	 */
+	g_free(plugin->error);
+	plugin->error = NULL;
+
 	if (unload_cb != NULL)
 		unload_cb(plugin, unload_cb_data);
 
@@ -758,6 +760,15 @@
 #endif /* PURPLE_PLUGINS */
 }
 
+void
+purple_plugin_disable(PurplePlugin *plugin)
+{
+	g_return_if_fail(plugin != NULL);
+
+	if (!g_list_find(plugins_to_disable, plugin))
+		plugins_to_disable = g_list_prepend(plugins_to_disable, plugin);
+}
+
 gboolean
 purple_plugin_reload(PurplePlugin *plugin)
 {
@@ -1223,14 +1234,14 @@
 #ifdef PURPLE_PLUGINS
 	GList *pl;
 	GList *files = NULL;
-	PurplePlugin *p;
 
 	for (pl = purple_plugins_get_loaded(); pl != NULL; pl = pl->next) {
-		p = pl->data;
+		PurplePlugin *plugin = pl->data;
 
-		if (p->info->type != PURPLE_PLUGIN_PROTOCOL &&
-			p->info->type != PURPLE_PLUGIN_LOADER) {
-				files = g_list_append(files, p->path);
+		if (plugin->info->type != PURPLE_PLUGIN_PROTOCOL &&
+		    plugin->info->type != PURPLE_PLUGIN_LOADER &&
+		    !g_list_find(plugins_to_disable, plugin)) {
+			files = g_list_append(files, plugin->path);
 		}
 	}
 
--- a/libpurple/plugin.h	Sun Oct 07 15:58:57 2007 +0000
+++ b/libpurple/plugin.h	Sun Oct 07 16:02:55 2007 +0000
@@ -292,6 +292,18 @@
 gboolean purple_plugin_unload(PurplePlugin *plugin);
 
 /**
+ * Disable a plugin.
+ *
+ * This function adds the plugin to a list of plugins to "disable at the next
+ * startup" by excluding said plugins from the list of plugins to save.  The
+ * UI needs to call purple_plugins_save_loaded() after calling this for it
+ * to have any effect.
+ *
+ * @since 2.3.0
+ */
+void purple_plugin_disable(PurplePlugin *plugin);
+
+/**
  * Reloads a plugin.
  *
  * @param plugin The old plugin handle.