Add -p and -P command line options for controlling plugin selection
This patch adds new -p (enable) and -P (disable) command line options to
select which plugins get loaded and which ones don't during bluetoothd
startup.
diff --git a/src/hcid.h b/src/hcid.h
index 85effdb..040411b 100644
--- a/src/hcid.h
+++ b/src/hcid.h
@@ -80,7 +80,8 @@
void set_pin_length(bdaddr_t *sba, int length);
-gboolean plugin_init(GKeyFile *config);
+gboolean plugin_init(GKeyFile *config, const char *enable,
+ const char *disable);
void plugin_cleanup(void);
void rfkill_init(void);
diff --git a/src/main.c b/src/main.c
index 5460c32..adbb374 100644
--- a/src/main.c
+++ b/src/main.c
@@ -257,6 +257,8 @@
}
static gchar *option_debug = NULL;
+static gchar *option_plugin = NULL;
+static gchar *option_noplugin = NULL;
static gboolean option_detach = TRUE;
static gboolean option_version = FALSE;
static gboolean option_udev = FALSE;
@@ -344,6 +346,10 @@
{ "debug", 'd', G_OPTION_FLAG_OPTIONAL_ARG,
G_OPTION_ARG_CALLBACK, parse_debug,
"Specify debug options to enable", "DEBUG" },
+ { "plugin", 'p', 0, G_OPTION_ARG_STRING, &option_plugin,
+ "Specify plugins to load", "NAME,..," },
+ { "noplugin", 'P', 0, G_OPTION_ARG_STRING, &option_noplugin,
+ "Specify plugins not to load", "NAME,..." },
{ "nodetach", 'n', G_OPTION_FLAG_REVERSE,
G_OPTION_ARG_NONE, &option_detach,
"Don't run as daemon in background" },
@@ -456,7 +462,7 @@
* the plugins might wanna expose some paths on the bus. However the
* best order of how to init various subsystems of the Bluetooth
* daemon needs to be re-worked. */
- plugin_init(config);
+ plugin_init(config, option_plugin, option_noplugin);
event_loop = g_main_loop_new(NULL, FALSE);
diff --git a/src/plugin.c b/src/plugin.c
index a63ce8e..3506553 100644
--- a/src/plugin.c
+++ b/src/plugin.c
@@ -82,41 +82,50 @@
return TRUE;
}
-static gboolean is_disabled(const char *name, char **list)
+static gboolean enable_plugin(const char *name, char **conf_disable,
+ char **cli_enable, char **cli_disable)
{
- int i;
-
- if (list == NULL)
- return FALSE;
-
- for (i = 0; list[i] != NULL; i++) {
- char *str;
- gboolean equal;
-
- if (g_str_equal(name, list[i]))
- return TRUE;
-
- str = g_strdup_printf("%s.so", list[i]);
-
- equal = g_str_equal(str, name);
-
- g_free(str);
-
- if (equal)
- return TRUE;
+ if (conf_disable) {
+ for (; *conf_disable; conf_disable++)
+ if (g_pattern_match_simple(*conf_disable, name))
+ break;
+ if (*conf_disable) {
+ info("Excluding (conf) %s", name);
+ return FALSE;
+ }
}
- return FALSE;
+ if (cli_disable) {
+ for (; *cli_disable; cli_disable++)
+ if (g_pattern_match_simple(*cli_disable, name))
+ break;
+ if (*cli_disable) {
+ info("Excluding (cli) %s", name);
+ return FALSE;
+ }
+ }
+
+ if (cli_enable) {
+ for (; *cli_enable; cli_enable++)
+ if (g_pattern_match_simple(*cli_enable, name))
+ break;
+ if (!*cli_enable) {
+ info("Ignoring (cli) %s", name);
+ return FALSE;
+ }
+ }
+
+ return TRUE;
}
#include "builtin.h"
-gboolean plugin_init(GKeyFile *config)
+gboolean plugin_init(GKeyFile *config, const char *enable, const char *disable)
{
GSList *list;
GDir *dir;
const gchar *file;
- gchar **disabled;
+ char **conf_disabled, **cli_disabled, **cli_enabled;
unsigned int i;
/* Make a call to BtIO API so its symbols got resolved before the
@@ -124,33 +133,40 @@
bt_io_error_quark();
if (config)
- disabled = g_key_file_get_string_list(config, "General",
+ conf_disabled = g_key_file_get_string_list(config, "General",
"DisablePlugins",
NULL, NULL);
else
- disabled = NULL;
+ conf_disabled = NULL;
+
+ if (enable)
+ cli_enabled = g_strsplit_set(enable, ", ", -1);
+ else
+ cli_enabled = NULL;
+
+ if (disable)
+ cli_disabled = g_strsplit_set(disable, ", ", -1);
+ else
+ cli_disabled = NULL;
DBG("Loading builtin plugins");
for (i = 0; __bluetooth_builtin[i]; i++) {
- if (is_disabled(__bluetooth_builtin[i]->name, disabled))
+ if (!enable_plugin(__bluetooth_builtin[i]->name, conf_disabled,
+ cli_enabled, cli_disabled))
continue;
add_plugin(NULL, __bluetooth_builtin[i]);
}
- if (strlen(PLUGINDIR) == 0) {
- g_strfreev(disabled);
+ if (strlen(PLUGINDIR) == 0)
goto start;
- }
DBG("Loading plugins %s", PLUGINDIR);
dir = g_dir_open(PLUGINDIR, 0, NULL);
- if (!dir) {
- g_strfreev(disabled);
+ if (!dir)
goto start;
- }
while ((file = g_dir_read_name(dir)) != NULL) {
struct bluetooth_plugin_desc *desc;
@@ -161,9 +177,6 @@
g_str_has_suffix(file, ".so") == FALSE)
continue;
- if (is_disabled(file, disabled))
- continue;
-
filename = g_build_filename(PLUGINDIR, file, NULL);
handle = dlopen(filename, RTLD_NOW);
@@ -183,14 +196,18 @@
continue;
}
+ if (!enable_plugin(desc->name, conf_disabled,
+ cli_enabled, cli_disabled)) {
+ dlclose(handle);
+ continue;
+ }
+
if (add_plugin(handle, desc) == FALSE)
dlclose(handle);
}
g_dir_close(dir);
- g_strfreev(disabled);
-
start:
for (list = plugins; list; list = list->next) {
struct bluetooth_plugin *plugin = list->data;
@@ -203,6 +220,10 @@
plugin->active = TRUE;
}
+ g_strfreev(conf_disabled);
+ g_strfreev(cli_enabled);
+ g_strfreev(cli_disabled);
+
return TRUE;
}