summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 08d98ff)
raw | patch | inline | side by side (parent: 08d98ff)
author | Sebastian Harl <sh@tokkee.org> | |
Thu, 21 May 2015 21:36:57 +0000 (23:36 +0200) | ||
committer | Sebastian Harl <sh@tokkee.org> | |
Thu, 21 May 2015 21:36:57 +0000 (23:36 +0200) |
That'll allow us to use different store objects in multiple places in the
future.
future.
diff --git a/src/core/store.c b/src/core/store.c
index 764c7c7a0e7604177f18a570d68529b0aba1caed..f6c65bcf7cd2604ac78889688186ebf3d2133b18 100644 (file)
--- a/src/core/store.c
+++ b/src/core/store.c
* private variables
*/
-static sdb_avltree_t *hosts = NULL;
-static pthread_rwlock_t host_lock = PTHREAD_RWLOCK_INITIALIZER;
+typedef struct {
+ sdb_object_t super;
+
+ /* hosts are the top-level entries and
+ * reference everything else */
+ sdb_avltree_t *hosts;
+ pthread_rwlock_t host_lock;
+} sdb_store_t;
+#define ST(obj) ((sdb_store_t *)(obj))
+
+sdb_store_t *global_store = NULL;
/*
* private types
static sdb_type_t metric_type;
static sdb_type_t attribute_type;
+static int
+store_init(sdb_object_t *obj, va_list __attribute__((unused)) ap)
+{
+ int err;
+ if (! (ST(obj)->hosts = sdb_avltree_create()))
+ return -1;
+ if ((err = pthread_rwlock_init(&ST(obj)->host_lock, /* attr = */ NULL))) {
+ char errbuf[128];
+ sdb_log(SDB_LOG_ERR, "store: Failed to initialize lock: %s",
+ sdb_strerror(err, errbuf, sizeof(errbuf)));
+ return -1;
+ }
+ return 0;
+} /* store_init */
+
+static void
+store_destroy(sdb_object_t *obj)
+{
+ int err;
+ if ((err = pthread_rwlock_destroy(&ST(obj)->host_lock))) {
+ char errbuf[128];
+ sdb_log(SDB_LOG_ERR, "store: Failed to destroy lock: %s",
+ sdb_strerror(err, errbuf, sizeof(errbuf)));
+ return;
+ }
+ sdb_avltree_destroy(ST(obj)->hosts);
+ ST(obj)->hosts = NULL;
+} /* store_destroy */
+
static int
store_obj_init(sdb_object_t *obj, va_list ap)
{
sdb_data_free_datum(&ATTR(obj)->value);
} /* attr_destroy */
+static sdb_type_t store_type = {
+ /* size = */ sizeof(sdb_store_t),
+ /* init = */ store_init,
+ /* destroy = */ store_destroy,
+};
+
static sdb_type_t host_type = {
/* size = */ sizeof(sdb_host_t),
/* init = */ host_init,
*/
static sdb_host_t *
-lookup_host(const char *name, bool canonicalize)
+lookup_host(sdb_store_t *st, const char *name, bool canonicalize)
{
sdb_host_t *host;
char *cname;
assert(name);
if (! canonicalize)
- return HOST(sdb_avltree_lookup(hosts, name));
+ return HOST(sdb_avltree_lookup(st->hosts, name));
cname = strdup(name);
cname = sdb_plugin_cname(cname);
return NULL;
}
- host = HOST(sdb_avltree_lookup(hosts, cname));
+ host = HOST(sdb_avltree_lookup(st->hosts, cname));
free(cname);
return host;
} /* lookup_host */
return 0;
} /* store_metric_store */
-/* The host_lock has to be acquired before calling this function. */
+/* The store's host_lock has to be acquired before calling this function. */
static sdb_avltree_t *
get_host_children(sdb_host_t *host, int type)
{
* public API
*/
+int
+sdb_store_init(void)
+{
+ if (global_store)
+ return 0;
+
+ global_store = ST(sdb_object_create("store", store_type));
+ if (! global_store) {
+ sdb_log(SDB_LOG_ERR, "store: Failed to allocate store");
+ return -1;
+ }
+ return 0;
+} /* sdb_store_init */
+
void
sdb_store_clear(void)
{
- sdb_avltree_destroy(hosts);
- hosts = NULL;
+ if (! global_store)
+ return;
+ sdb_avltree_clear(global_store->hosts);
} /* sdb_store_clear */
int
char *cname = NULL;
int status = 0;
- if (! name)
+ if ((! global_store) || (! name))
return -1;
cname = sdb_plugin_cname(strdup(name));
return -1;
}
- pthread_rwlock_wrlock(&host_lock);
- if (! hosts)
- if (! (hosts = sdb_avltree_create()))
- status = -1;
-
- if (! status)
- status = store_obj(NULL, hosts, SDB_HOST, cname, last_update, NULL);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ status = store_obj(NULL, global_store->hosts,
+ SDB_HOST, cname, last_update, NULL);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (sdb_plugin_store_host(name, last_update))
status = -1;
{
sdb_host_t *host;
- if (! name)
- return NULL;
+ if ((! global_store) || (! name))
+ return false;
- host = lookup_host(name, /* canonicalize = */ 0);
+ host = lookup_host(global_store, name, /* canonicalize = */ 0);
sdb_object_deref(SDB_OBJ(host));
return host != NULL;
} /* sdb_store_has_host */
{
sdb_host_t *host;
- if (! name)
+ if ((! global_store) || (! name))
return NULL;
- host = lookup_host(name, /* canonicalize = */ 0);
+ host = lookup_host(global_store, name, /* canonicalize = */ 0);
if (! host)
return NULL;
sdb_avltree_t *attrs;
int status = 0;
- if ((! hostname) || (! key))
+ if ((! global_store) || (! hostname) || (! key))
return -1;
- pthread_rwlock_wrlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
attrs = get_host_children(host, SDB_ATTRIBUTE);
if (! attrs) {
sdb_log(SDB_LOG_ERR, "store: Failed to store attribute '%s' - "
status = store_attr(STORE_OBJ(host), attrs, key, value, last_update);
sdb_object_deref(SDB_OBJ(host));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (sdb_plugin_store_attribute(hostname, key, value, last_update))
status = -1;
int status = 0;
- if ((! hostname) || (! name))
+ if ((! global_store) || (! hostname) || (! name))
return -1;
- pthread_rwlock_wrlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
services = get_host_children(host, SDB_SERVICE);
if (! services) {
sdb_log(SDB_LOG_ERR, "store: Failed to store service '%s' - "
name, last_update, NULL);
sdb_object_deref(SDB_OBJ(host));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (status)
return status;
sdb_avltree_t *services;
int status = 0;
- if ((! hostname) || (! service) || (! key))
+ if ((! global_store) || (! hostname) || (! service) || (! key))
return -1;
- pthread_rwlock_wrlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
services = get_host_children(host, SDB_SERVICE);
sdb_object_deref(SDB_OBJ(host));
if (! services) {
sdb_log(SDB_LOG_ERR, "store: Failed to store attribute '%s' "
"for service '%s' - host '%ss' not found",
key, service, hostname);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return -1;
}
key, value, last_update);
sdb_object_deref(SDB_OBJ(svc));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (sdb_plugin_store_service_attribute(hostname, service,
key, value, last_update))
int status = 0;
- if ((! hostname) || (! name))
+ if ((! global_store) || (! hostname) || (! name))
return -1;
if (store) {
store = NULL;
}
- pthread_rwlock_wrlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
metrics = get_host_children(host, SDB_METRIC);
if (! metrics) {
sdb_log(SDB_LOG_ERR, "store: Failed to store metric '%s' - "
sdb_object_deref(SDB_OBJ(host));
if (status) {
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return status;
}
if (store)
if (store_metric_store(metric, store))
status = -1;
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (sdb_plugin_store_metric(hostname, name, store, last_update))
status = -1;
sdb_metric_t *m;
int status = 0;
- if ((! hostname) || (! metric) || (! key))
+ if ((! global_store) || (! hostname) || (! metric) || (! key))
return -1;
- pthread_rwlock_wrlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_wrlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
metrics = get_host_children(host, SDB_METRIC);
sdb_object_deref(SDB_OBJ(host));
if (! metrics) {
sdb_log(SDB_LOG_ERR, "store: Failed to store attribute '%s' "
"for metric '%s' - host '%s' not found",
key, metric, hostname);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return -1;
}
key, value, last_update);
sdb_object_deref(SDB_OBJ(m));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
if (sdb_plugin_store_metric_attribute(hostname, metric,
key, value, last_update))
int status = 0;
- if ((! hostname) || (! metric) || (! opts) || (! buf))
+ if ((! global_store) || (! hostname) || (! metric) || (! opts) || (! buf))
return -1;
- pthread_rwlock_rdlock(&host_lock);
- host = lookup_host(hostname, /* canonicalize = */ 1);
+ pthread_rwlock_rdlock(&global_store->host_lock);
+ host = lookup_host(global_store, hostname, /* canonicalize = */ 1);
metrics = get_host_children(host, SDB_METRIC);
sdb_object_deref(SDB_OBJ(host));
if (! metrics) {
sdb_log(SDB_LOG_ERR, "store: Failed to fetch time-series '%s/%s' "
"- host '%s' not found", hostname, metric, hostname);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return -1;
}
if (! m) {
sdb_log(SDB_LOG_ERR, "store: Failed to fetch time-series '%s/%s' "
"- metric '%s' not found", hostname, metric, metric);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return -1;
}
"- no data-store configured for the stored metric",
hostname, metric);
sdb_object_deref(SDB_OBJ(m));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return -1;
}
strncpy(type, m->store.type, sizeof(type));
strncpy(id, m->store.id, sizeof(id));
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
ts = sdb_plugin_fetch_timeseries(type, id, opts);
if (! ts) {
sdb_avltree_iter_t *host_iter = NULL;
int status = 0;
- if (! cb)
+ if ((! global_store) || (! cb))
return -1;
if ((type != SDB_HOST) && (type != SDB_SERVICE) && (type != SDB_METRIC)) {
@@ -1008,13 +1063,10 @@ sdb_store_scan(int type, sdb_store_matcher_t *m, sdb_store_matcher_t *filter,
return -1;
}
- pthread_rwlock_rdlock(&host_lock);
-
- if (hosts) {
- host_iter = sdb_avltree_get_iter(hosts);
- if (! host_iter)
- status = -1;
- }
+ pthread_rwlock_rdlock(&global_store->host_lock);
+ host_iter = sdb_avltree_get_iter(global_store->hosts);
+ if (! host_iter)
+ status = -1;
/* has_next returns false if the iterator is NULL */
while (sdb_avltree_iter_has_next(host_iter)) {
}
sdb_avltree_iter_destroy(host_iter);
- pthread_rwlock_unlock(&host_lock);
+ pthread_rwlock_unlock(&global_store->host_lock);
return status;
} /* sdb_store_scan */
index c52299e806314a951df6fbb670e7b098f7e371cd..4a0960c1cbe0055f77c1c1c6d64a9f32aa566b82 100644 (file)
--- a/src/include/core/store.h
+++ b/src/include/core/store.h
sdb_object_t *user_data);
} sdb_store_writer_t;
+/*
+ * sdb_store_init:
+ * Initialize the store sub-system. This function has to be called before
+ * doing any other store operations.
+ *
+ * Returns:
+ * - 0 on success
+ * - a negative value else
+ */
+int
+sdb_store_init(void);
+
/*
* sdb_store_clear:
* Clear the entire store and remove all stored objects.
index 759eee2f5652ebee72c9131d22a05ddbf8f704b2..cc3525e30ef4374e3c904797cccd176de2e94043 100644 (file)
--- a/src/tools/sysdbd/main.c
+++ b/src/tools/sysdbd/main.c
if (sdb_ssl_init())
exit(1);
+ if (sdb_store_init())
+ exit(1);
sdb_plugin_init_all();
plugin_main_loop.default_interval = SECS_TO_SDB_TIME(60);
index 679fb548418092fbe1377cd9232dadf07e1af928..b15809a589bc890dd36ff5c8809bdf71b75cfd84 100644 (file)
size_t i;
+ sdb_store_init();
+
for (i = 0; i < SDB_STATIC_ARRAY_LEN(hosts); ++i) {
int status = sdb_store_host(hosts[i], 1);
ck_assert(status == 0);
index 113d3a0010d0f5669e53d68aa6dbd2fdad753858..ebb2daf1d22ec7cee81e267d97ca476612b5abe9 100644 (file)
{
sdb_data_t datum;
+ sdb_store_init();
+
sdb_store_host("h1", 1 * SDB_INTERVAL_SECOND);
sdb_store_host("h2", 3 * SDB_INTERVAL_SECOND);
index b4c6015b7bfb0dcfe2d338eb05af51555491efca..913e6b78a0905bb803a5d7073e3cc27c4a457904 100644 (file)
size_t i;
+ sdb_store_init();
+
for (i = 0; i < SDB_STATIC_ARRAY_LEN(hosts); ++i) {
int status = sdb_store_host(hosts[i], 1);
fail_unless(status == 0,
index dbf220cef4f26d718a505b8a9678812bbd0a1360..8308f3334f39d7c2c8cd71362f5903eab399c412 100644 (file)
--- a/t/unit/core/store_test.c
+++ b/t/unit/core/store_test.c
#include <string.h>
#include <strings.h>
+static void
+init(void)
+{
+ sdb_store_init();
+}
+
static void
populate(void)
{
sdb_data_t datum;
+ sdb_store_init();
+
sdb_store_host("h1", 1);
sdb_store_host("h2", 3);
tcase_add_test(tc, test_get_child);
tcase_add_test(tc, test_interval);
tcase_add_test(tc, test_scan);
- tcase_add_unchecked_fixture(tc, NULL, sdb_store_clear);
+ tcase_add_unchecked_fixture(tc, init, sdb_store_clear);
ADD_TCASE(tc);
}
TEST_MAIN_END
index 8872e5b6e13a0f2879430e20e65f7c7f1bf27ebf..4be05630136991215e191a573d892d7f3c142697 100644 (file)
{
sdb_data_t datum;
+ sdb_store_init();
+
sdb_store_host("h1", 1 * SDB_INTERVAL_SECOND);
sdb_store_host("h2", 3 * SDB_INTERVAL_SECOND);