Example #1
0
static int
window_closed_cb()
{
	purple_plugin_unload(my_plugin, NULL);

	return FALSE;
}
Example #2
0
static void
plugin_toggled_cb(GntWidget *tree, PurplePlugin *plugin, gpointer null)
{
	GError *error = NULL;

	if (gnt_tree_get_choice(GNT_TREE(tree), plugin))
	{
		if (!purple_plugin_load(plugin, &error)) {
			purple_notify_error(NULL, _("ERROR"), _("loading plugin failed"), error->message, NULL);
			gnt_tree_set_choice(GNT_TREE(tree), plugin, FALSE);
			g_error_free(error);
		}
	}
	else
	{
		if (!purple_plugin_unload(plugin, &error)) {
			purple_notify_error(NULL, _("ERROR"), _("unloading plugin failed"), error->message, NULL);
			purple_plugin_disable(plugin);
			gnt_tree_set_choice(GNT_TREE(tree), plugin, TRUE);
			g_error_free(error);
		}

		finch_plugin_pref_close(plugin);
	}
	decide_conf_button(plugin);
	finch_plugins_save_loaded();
}
Example #3
0
static void
plugin_toggled_cb(GntWidget *tree, PurplePlugin *plugin, gpointer null)
{
	if (gnt_tree_get_choice(GNT_TREE(tree), plugin))
	{
		if (!purple_plugin_load(plugin)) {
			purple_notify_error(NULL, _("ERROR"), _("loading plugin failed"), NULL);
			gnt_tree_set_choice(GNT_TREE(tree), plugin, FALSE);
		}
	}
	else
	{
		GntWidget *win;

		if (!purple_plugin_unload(plugin)) {
			purple_notify_error(NULL, _("ERROR"), _("unloading plugin failed"), NULL);
			purple_plugin_disable(plugin);
			gnt_tree_set_choice(GNT_TREE(tree), plugin, TRUE);
		}

		if (confwins && (win = g_hash_table_lookup(confwins, plugin)) != NULL)
		{
			gnt_widget_destroy(win);
		}
	}
	decide_conf_button(plugin);
	finch_plugins_save_loaded();
}
Example #4
0
void
purple_plugins_unload_all(void)
{
#ifdef PURPLE_PLUGINS

	while (loaded_plugins != NULL)
		purple_plugin_unload(loaded_plugins->data);

#endif /* PURPLE_PLUGINS */
}
Example #5
0
static gboolean
plugin_unload(PurplePlugin *plugin)
{
    PurplePlugin *buddynote = NULL;

    buddynote = purple_plugins_find_with_id("core-plugin_pack-buddynote");

    purple_plugin_unload(buddynote);

    return TRUE;
}
Example #6
0
void
purple_plugins_unload(PurplePluginType type)
{
#ifdef PURPLE_PLUGINS
	GList *l;

	for (l = plugins; l; l = l->next) {
		PurplePlugin *plugin = l->data;
		if (plugin->info->type == type && purple_plugin_is_loaded(plugin))
			purple_plugin_unload(plugin);
	}

#endif /* PURPLE_PLUGINS */
}
Example #7
0
gboolean
purple_plugin_reload(PurplePlugin *plugin)
{
#ifdef PURPLE_PLUGINS
	g_return_val_if_fail(plugin != NULL, FALSE);
	g_return_val_if_fail(purple_plugin_is_loaded(plugin), FALSE);

	if (!purple_plugin_unload(plugin))
		return FALSE;

	if (!purple_plugin_load(plugin))
		return FALSE;

	return TRUE;
#else
	return TRUE;
#endif /* !PURPLE_PLUGINS */
}
Example #8
0
void
purple_plugin_destroy(PurplePlugin *plugin)
{
#ifdef PURPLE_PLUGINS
	g_return_if_fail(plugin != NULL);

	if (purple_plugin_is_loaded(plugin))
		purple_plugin_unload(plugin);

	plugins = g_list_remove(plugins, plugin);

	if (load_queue != NULL)
		load_queue = g_list_remove(load_queue, plugin);

	/* true, this may leak a little memory if there is a major version
	 * mismatch, but it's a lot better than trying to free something
	 * we shouldn't, and crashing while trying to load an old plugin */
	if(plugin->info == NULL || plugin->info->magic != PURPLE_PLUGIN_MAGIC ||
			plugin->info->major_version != PURPLE_MAJOR_VERSION)
	{
		if(plugin->handle)
			g_module_close(plugin->handle);

		g_free(plugin->path);
		g_free(plugin->error);

		PURPLE_DBUS_UNREGISTER_POINTER(plugin);

		g_free(plugin);
		return;
	}

	if (plugin->info != NULL)
		g_list_free(plugin->info->dependencies);

	if (plugin->native_plugin)
	{
		if (plugin->info != NULL && plugin->info->type == PURPLE_PLUGIN_LOADER)
		{
			PurplePluginLoaderInfo *loader_info;
			GList *exts, *l, *next_l;
			PurplePlugin *p2;

			loader_info = PURPLE_PLUGIN_LOADER_INFO(plugin);

			if (loader_info != NULL && loader_info->exts != NULL)
			{
				for (exts = PURPLE_PLUGIN_LOADER_INFO(plugin)->exts;
					 exts != NULL;
					 exts = exts->next) {

					for (l = purple_plugins_get_all(); l != NULL; l = next_l)
					{
						next_l = l->next;

						p2 = l->data;

						if (p2->path != NULL &&
							has_file_extension(p2->path, exts->data))
						{
							purple_plugin_destroy(p2);
						}
					}
				}

				g_list_free(loader_info->exts);
				loader_info->exts = NULL;
			}

			plugin_loaders = g_list_remove(plugin_loaders, plugin);
		}

		if (plugin->info != NULL && plugin->info->destroy != NULL)
			plugin->info->destroy(plugin);

		/*
		 * I find it extremely useful to do this when using valgrind, as
		 * it keeps all the plugins open, meaning that valgrind is able to
		 * resolve symbol names in leak traces from plugins.
		 */
		if (!g_getenv("PURPLE_LEAKCHECK_HELP") && !RUNNING_ON_VALGRIND)
		{
			if (plugin->handle != NULL)
				g_module_close(plugin->handle);
		}
	}
	else
	{
		PurplePlugin *loader;
		PurplePluginLoaderInfo *loader_info;

		loader = find_loader_for_plugin(plugin);

		if (loader != NULL)
		{
			loader_info = PURPLE_PLUGIN_LOADER_INFO(loader);

			if (loader_info->destroy != NULL)
				loader_info->destroy(plugin);
		}
	}

	g_free(plugin->path);
	g_free(plugin->error);

	PURPLE_DBUS_UNREGISTER_POINTER(plugin);

	g_free(plugin);
#endif /* !PURPLE_PLUGINS */
}
Example #9
0
gboolean
purple_plugin_unload(PurplePlugin *plugin)
{
#ifdef PURPLE_PLUGINS
	GList *l;
	GList *ll;

	g_return_val_if_fail(plugin != NULL, FALSE);
	g_return_val_if_fail(purple_plugin_is_loaded(plugin), FALSE);

	purple_debug_info("plugins", "Unloading plugin %s\n", plugin->info->name);

	/* Unload all plugins that depend on this plugin. */
	for (l = plugin->dependent_plugins; l != NULL; l = ll) {
		const char * dep_name = (const char *)l->data;
		PurplePlugin *dep_plugin;

		/* Store a pointer to the next element in the list.
		 * This is because we'll be modifying this list in the loop. */
		ll = l->next;

		dep_plugin = purple_plugins_find_with_id(dep_name);

		if (dep_plugin != NULL && purple_plugin_is_loaded(dep_plugin))
		{
			if (!purple_plugin_unload(dep_plugin))
			{
				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
			{
#if 0
				/* This isn't necessary. This has already been done when unloading dep_plugin. */
				plugin->dependent_plugins = g_list_delete_link(plugin->dependent_plugins, l);
#endif
			}
		}
	}

	/* Remove this plugin from each dependency's dependent_plugins list. */
	for (l = plugin->info->dependencies; l != NULL; l = l->next)
	{
		const char *dep_name = (const char *)l->data;
		PurplePlugin *dependency;

		dependency = purple_plugins_find_with_id(dep_name);

		if (dependency != NULL)
			dependency->dependent_plugins = g_list_remove(dependency->dependent_plugins, plugin->info->id);
		else
			purple_debug_error("plugins", "Unable to remove from dependency list for %s\n", dep_name);
	}

	if (plugin->native_plugin) {
		if (plugin->info->unload && !plugin->info->unload(plugin))
			return FALSE;

		if (plugin->info->type == PURPLE_PLUGIN_PROTOCOL) {
			PurplePluginProtocolInfo *prpl_info;
			GList *l;

			prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(plugin);

			for (l = prpl_info->user_splits; l != NULL; l = l->next)
				purple_account_user_split_destroy(l->data);

			for (l = prpl_info->protocol_options; l != NULL; l = l->next)
				purple_account_option_destroy(l->data);

			if (prpl_info->user_splits != NULL) {
				g_list_free(prpl_info->user_splits);
				prpl_info->user_splits = NULL;
			}

			if (prpl_info->protocol_options != NULL) {
				g_list_free(prpl_info->protocol_options);
				prpl_info->protocol_options = NULL;
			}
		}
	} else {
		PurplePlugin *loader;
		PurplePluginLoaderInfo *loader_info;

		loader = find_loader_for_plugin(plugin);

		if (loader == NULL)
			return FALSE;

		loader_info = PURPLE_PLUGIN_LOADER_INFO(loader);

		if (loader_info->unload && !loader_info->unload(plugin))
			return FALSE;
	}

	/* cancel any pending dialogs the plugin has */
	purple_request_close_with_handle(plugin);
	purple_notify_close_with_handle(plugin);

	purple_signals_disconnect_by_handle(plugin);
	purple_plugin_ipc_unregister_all(plugin);

	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;

	purple_signal_emit(purple_plugins_get_handle(), "plugin-unload", plugin);

	purple_prefs_disconnect_by_handle(plugin);

	return TRUE;
#else
	return TRUE;
#endif /* PURPLE_PLUGINS */
}