X-Git-Url: https://git.tokkee.org/?a=blobdiff_plain;f=src%2Fcore%2Fplugin.c;h=20fe61cd523dfe6db6229e3996e332a13cc7ca5e;hb=49b5a4d2e8e4fb1e4f67c2a368d8d2e3e76b765f;hp=b3d5973178dffed19411af5d5acea45a99b718e3;hpb=4436642effe44c7d891bdcc4b207aeddb1c0e43d;p=sysdb.git diff --git a/src/core/plugin.c b/src/core/plugin.c index b3d5973..20fe61c 100644 --- a/src/core/plugin.c +++ b/src/core/plugin.c @@ -50,32 +50,14 @@ #include +/* helper to access info attributes */ +#define INFO_GET(i, attr) \ + ((i)->attr ? (i)->attr : #attr" not set") + /* * private data types */ -struct sdb_plugin_info { - char *plugin_name; - char *filename; - - /* public attributes */ - char *name; - - char *description; - char *copyright; - char *license; - - int version; - int plugin_version; -}; -#define SDB_PLUGIN_INFO_INIT { \ - /* plugin_name */ NULL, /* filename */ NULL, \ - /* name */ NULL, /* desc */ NULL, \ - /* copyright */ NULL, /* license */ NULL, \ - /* version */ -1, /* plugin_version */ -1 } -#define INFO_GET(i, attr) \ - ((i)->attr ? (i)->attr : #attr" not set") - typedef struct { sdb_object_t super; sdb_plugin_ctx_t public; @@ -125,7 +107,7 @@ static sdb_plugin_ctx_t plugin_default_ctx = SDB_PLUGIN_CTX_INIT; static sdb_plugin_info_t plugin_default_info = SDB_PLUGIN_INFO_INIT; static pthread_key_t plugin_ctx_key; -static _Bool plugin_ctx_key_initialized = 0; +static bool plugin_ctx_key_initialized = 0; /* a list of the plugin contexts of all registered plugins */ static sdb_llist_t *all_plugins = NULL; @@ -136,6 +118,7 @@ static sdb_llist_t *collector_list = NULL; static sdb_llist_t *cname_list = NULL; static sdb_llist_t *shutdown_list = NULL; static sdb_llist_t *log_list = NULL; +static sdb_llist_t *ts_fetcher_list = NULL; static struct { const char *type; @@ -165,8 +148,6 @@ plugin_info_clear(sdb_plugin_info_t *info) if (info->filename) free(info->filename); - if (info->name) - free(info->name); if (info->description) free(info->description); if (info->copyright) @@ -525,9 +506,11 @@ module_load(const char *basedir, const char *name, sdb_llist_append(all_plugins, SDB_OBJ(ctx)); sdb_log(SDB_LOG_INFO, "core: Successfully loaded " - "plugin '%s' v%i (%s)\n\t%s\n\tLicense: %s", - INFO_GET(&ctx->info, name), ctx->info.plugin_version, - INFO_GET(&ctx->info, description), + "plugin %s v%i (%s)", ctx->info.plugin_name, + ctx->info.plugin_version, + INFO_GET(&ctx->info, description)); + sdb_log(SDB_LOG_INFO, "core: Plugin %s: %s, License: %s", + ctx->info.plugin_name, INFO_GET(&ctx->info, copyright), INFO_GET(&ctx->info, license)); @@ -539,6 +522,18 @@ module_load(const char *basedir, const char *name, return 0; } /* module_load */ +static char * +plugin_get_name(const char *name, char *buf, size_t bufsize) +{ + ctx_t *ctx = ctx_get(); + + if (ctx) + snprintf(buf, bufsize, "%s::%s", ctx->info.plugin_name, name); + else + snprintf(buf, bufsize, "core::%s", name); + return buf; +} /* plugin_get_name */ + static int plugin_add_callback(sdb_llist_t **list, const char *type, const char *name, void *callback, sdb_object_t *user_data) @@ -608,7 +603,7 @@ sdb_plugin_load(const char *basedir, const char *name, return status; sdb_log(SDB_LOG_INFO, "core: Successfully reloaded plugin " - "'%s' (%s)", INFO_GET(&ctx->info, name), + "'%s' (%s)", ctx->info.plugin_name, INFO_GET(&ctx->info, description)); ctx_set(old_ctx); } @@ -630,16 +625,6 @@ sdb_plugin_set_info(sdb_plugin_info_t *info, int type, ...) va_start(ap, type); switch (type) { - case SDB_PLUGIN_INFO_NAME: - { - char *name = va_arg(ap, char *); - if (name) { - if (info->name) - free(info->name); - info->name = strdup(name); - } - } - break; case SDB_PLUGIN_INFO_DESC: { char *desc = va_arg(ap, char *); @@ -689,9 +674,16 @@ sdb_plugin_set_info(sdb_plugin_info_t *info, int type, ...) } /* sdb_plugin_set_info */ int -sdb_plugin_register_config(const char *name, sdb_plugin_config_cb callback) +sdb_plugin_register_config(sdb_plugin_config_cb callback) { - return plugin_add_callback(&config_list, "init", name, + ctx_t *ctx = ctx_get(); + + if (! ctx) { + sdb_log(SDB_LOG_ERR, "core: Invalid attempt to register a " + "config callback from outside a plugin"); + return -1; + } + return plugin_add_callback(&config_list, "init", ctx->info.plugin_name, (void *)callback, NULL); } /* sdb_plugin_register_config */ @@ -699,7 +691,9 @@ int sdb_plugin_register_init(const char *name, sdb_plugin_init_cb callback, sdb_object_t *user_data) { - return plugin_add_callback(&init_list, "init", name, + char cb_name[1024]; + return plugin_add_callback(&init_list, "init", + plugin_get_name(name, cb_name, sizeof(cb_name)), (void *)callback, user_data); } /* sdb_plugin_register_init */ @@ -707,7 +701,9 @@ int sdb_plugin_register_shutdown(const char *name, sdb_plugin_shutdown_cb callback, sdb_object_t *user_data) { - return plugin_add_callback(&shutdown_list, "shutdown", name, + char cb_name[1024]; + return plugin_add_callback(&shutdown_list, "shutdown", + plugin_get_name(name, cb_name, sizeof(cb_name)), (void *)callback, user_data); } /* sdb_plugin_register_shutdown */ @@ -715,22 +711,27 @@ int sdb_plugin_register_log(const char *name, sdb_plugin_log_cb callback, sdb_object_t *user_data) { - return plugin_add_callback(&log_list, "log", name, (void *)callback, - user_data); + char cb_name[1024]; + return plugin_add_callback(&log_list, "log", + plugin_get_name(name, cb_name, sizeof(cb_name)), + callback, user_data); } /* sdb_plugin_register_log */ int sdb_plugin_register_cname(const char *name, sdb_plugin_cname_cb callback, sdb_object_t *user_data) { - return plugin_add_callback(&cname_list, "cname", name, (void *)callback, - user_data); + char cb_name[1024]; + return plugin_add_callback(&cname_list, "cname", + plugin_get_name(name, cb_name, sizeof(cb_name)), + callback, user_data); } /* sdb_plugin_register_cname */ int sdb_plugin_register_collector(const char *name, sdb_plugin_collector_cb callback, const sdb_time_t *interval, sdb_object_t *user_data) { + char cb_name[1024]; sdb_object_t *obj; if ((! name) || (! callback)) @@ -741,7 +742,9 @@ sdb_plugin_register_collector(const char *name, sdb_plugin_collector_cb callback if (! collector_list) return -1; - obj = sdb_object_create(name, sdb_plugin_collector_cb_type, + plugin_get_name(name, cb_name, sizeof(cb_name)); + + obj = sdb_object_create(cb_name, sdb_plugin_collector_cb_type, &collector_list, "collector", callback, user_data); if (! obj) return -1; @@ -749,12 +752,16 @@ sdb_plugin_register_collector(const char *name, sdb_plugin_collector_cb callback if (interval) SDB_PLUGIN_CCB(obj)->ccb_interval = *interval; else { - sdb_time_t tmp = sdb_plugin_get_ctx().interval; + ctx_t *ctx = ctx_get(); - if (tmp > 0) - SDB_PLUGIN_CCB(obj)->ccb_interval = tmp; - else - SDB_PLUGIN_CCB(obj)->ccb_interval = 0; + if (! ctx) { + sdb_log(SDB_LOG_ERR, "core: Cannot determine interval " + "for collector %s; none specified and no plugin " + "context found", cb_name); + return -1; + } + + SDB_PLUGIN_CCB(obj)->ccb_interval = ctx->public.interval; } if (! (SDB_PLUGIN_CCB(obj)->ccb_next_update = sdb_gettime())) { @@ -775,11 +782,19 @@ sdb_plugin_register_collector(const char *name, sdb_plugin_collector_cb callback sdb_object_deref(obj); sdb_log(SDB_LOG_INFO, "core: Registered collector callback '%s' " - "(interval = %.3fs).", name, + "(interval = %.3fs).", cb_name, SDB_TIME_TO_DOUBLE(SDB_PLUGIN_CCB(obj)->ccb_interval)); return 0; } /* sdb_plugin_register_collector */ +int +sdb_plugin_register_ts_fetcher(const char *name, + sdb_plugin_fetch_ts_cb callback, sdb_object_t *user_data) +{ + return plugin_add_callback(&ts_fetcher_list, "time-series fetcher", + name, callback, user_data); +} /* sdb_plugin_register_ts_fetcher */ + sdb_plugin_ctx_t sdb_plugin_get_ctx(void) { @@ -812,6 +827,16 @@ sdb_plugin_set_ctx(sdb_plugin_ctx_t ctx, sdb_plugin_ctx_t *old) return 0; } /* sdb_plugin_set_ctx */ +const sdb_plugin_info_t * +sdb_plugin_current(void) +{ + ctx_t *ctx = ctx_get(); + + if (! ctx) + return NULL; + return &ctx->info; +} /* sdb_plugin_current */ + int sdb_plugin_configure(const char *name, oconfig_item_t *ci) { @@ -829,7 +854,9 @@ sdb_plugin_configure(const char *name, oconfig_item_t *ci) if (! plugin) { ctx_t *ctx = CTX(sdb_llist_search_by_name(all_plugins, name)); if (! ctx) - sdb_log(SDB_LOG_ERR, "core: Plugin '%s' not loaded.", name); + sdb_log(SDB_LOG_ERR, "core: Cannot configure unknown " + "plugin '%s'. Missing 'LoadPlugin \"%s\"'?", + name, name); else sdb_log(SDB_LOG_ERR, "core: Plugin '%s' did not register " "a config callback.", name); @@ -1113,7 +1140,7 @@ sdb_plugin_log(int prio, const char *msg) sdb_llist_iter_t *iter; int ret = -1; - _Bool logged = 0; + bool logged = 0; if (! msg) return 0; @@ -1183,5 +1210,33 @@ sdb_plugin_logf(int prio, const char *fmt, ...) return ret; } /* sdb_plugin_logf */ +sdb_timeseries_t * +sdb_plugin_fetch_timeseries(const char *type, const char *id, + sdb_timeseries_opts_t *opts) +{ + sdb_plugin_cb_t *plugin; + sdb_plugin_fetch_ts_cb callback; + sdb_timeseries_t *ts; + + ctx_t *old_ctx; + + if ((! type) || (! id) || (! opts)) + return NULL; + + plugin = SDB_PLUGIN_CB(sdb_llist_search_by_name(ts_fetcher_list, type)); + if (! plugin) { + sdb_log(SDB_LOG_ERR, "core: Cannot fetch time-series of type %s: " + "no such plugin loaded", type); + errno = ENOENT; + return NULL; + } + + old_ctx = ctx_set(plugin->cb_ctx); + callback = (sdb_plugin_fetch_ts_cb)plugin->cb_callback; + ts = callback(id, opts, plugin->cb_user_data); + ctx_set(old_ctx); + return ts; +} /* sdb_plugin_fetch_timeseries */ + /* vim: set tw=78 sw=4 ts=4 noexpandtab : */