summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 2846042)
raw | patch | inline | side by side (parent: 2846042)
author | Francesco Romani <fromani@redhat.com> | |
Mon, 21 Nov 2016 08:30:45 +0000 (09:30 +0100) | ||
committer | Francesco Romani <fromani@redhat.com> | |
Wed, 30 Nov 2016 09:27:00 +0000 (10:27 +0100) |
Add support to register more than one read callbacks in the
reader thread pool.
The default configuration is to use just one read callback,
for backward compatibility. No user-visible changes are expected
in this scenario.
Signed-off-by: Francesco Romani <fromani@redhat.com>
reader thread pool.
The default configuration is to use just one read callback,
for backward compatibility. No user-visible changes are expected
in this scenario.
Signed-off-by: Francesco Romani <fromani@redhat.com>
src/collectd.conf.in | patch | blob | history | |
src/collectd.conf.pod | patch | blob | history | |
src/virt.c | patch | blob | history |
diff --git a/src/collectd.conf.in b/src/collectd.conf.in
index e5b96435991d672874b5732cc951d2f2f225b4e6..8c1b10ddecfe82c74ee94e745170520c4c1f26b2 100644 (file)
--- a/src/collectd.conf.in
+++ b/src/collectd.conf.in
# HostnameFormat name
# InterfaceFormat name
# PluginInstanceFormat name
+# Instances 1
#</Plugin>
#<Plugin vmem>
diff --git a/src/collectd.conf.pod b/src/collectd.conf.pod
index 27c4e16ec3cd52bc329869b23e5901c92ea6330e..597bbe8cbaa0ffeda0bf4938f158b0731d3e5a3a 100644 (file)
--- a/src/collectd.conf.pod
+++ b/src/collectd.conf.pod
For example B<name uuid> means to concatenate the guest name and UUID
(with a literal colon character between, thus I<"foo:1234-1234-1234-1234">).
+=item B<Instances> B<integer>
+
+How many read instances you want to use for this plugin. The default is one,
+and the sensible setting is a multiple of the B<ReadThreads> value.
+If you are not sure, just use the default setting.
+
=back
=head2 Plugin C<vmem>
diff --git a/src/virt.c b/src/virt.c
index 2744db07e323cc57fdb719182afd4bdf19f6fca3..ae5a247c3f118ca5531311d09634bd2d3722ede9 100644 (file)
--- a/src/virt.c
+++ b/src/virt.c
"PluginInstanceFormat",
+ "Instances",
+
NULL};
#define NR_CONFIG_KEYS ((sizeof config_keys / sizeof config_keys[0]) - 1)
int nr_interface_devices;
};
-static struct lv_read_state read_state = {
- NULL, 0, NULL, 0, NULL, 0,
-};
-
static void free_domains(struct lv_read_state *state);
static int add_domain(struct lv_read_state *state, virDomainPtr dom);
const char *path, const char *address,
unsigned int number);
+#define PARTITION_TAG_MAX_LEN 32
+struct lv_read_instance {
+ struct lv_read_state read_state;
+ char tag[PARTITION_TAG_MAX_LEN];
+ size_t id;
+};
+
+struct lv_user_data {
+ struct lv_read_instance inst;
+ user_data_t ud;
+};
+
+#define NR_INSTANCES_DEFAULT 1
+#define NR_INSTANCES_MAX 128
+static size_t nr_instances = NR_INSTANCES_DEFAULT;
+static struct lv_user_data lv_read_user_data[NR_INSTANCES_MAX];
+
/* HostnameFormat. */
#define HF_MAX_FIELDS 3
submit(dom, type, devname, values, STATIC_ARRAY_SIZE(values));
} /* void submit_derive2 */
-static int lv_init(void) {
- if (virInitialize() != 0)
- return -1;
- else
- return 0;
-}
-
static int lv_config(const char *key, const char *value) {
if (virInitialize() != 0)
return 1;
return 0;
}
+ if (strcasecmp(key, "Instances") == 0) {
+ char *eptr = NULL;
+ long val = strtol(value, &eptr, 10);
+ if (eptr == NULL || *eptr != '\0')
+ return 1;
+ if (val <= 0) {
+ ERROR(PLUGIN_NAME " plugin: Instances <= 0 makes no sense.");
+ return 1;
+ }
+ if (val > NR_INSTANCES_MAX) {
+ ERROR(PLUGIN_NAME " plugin: Instances=%li > NR_INSTANCES_MAX=%i"
+ " use a lower setting or recompile the plugin.",
+ val, NR_INSTANCES_MAX);
+ return 1;
+ }
+ nr_instances = (size_t)val;
+ return 0;
+ }
+
/* Unrecognised option. */
return -1;
}
-static int lv_read(void) {
+static int lv_read(user_data_t *ud) {
time_t t;
- struct lv_read_state *state = &read_state;
+ struct lv_read_instance *inst = ud->data;
+ struct lv_read_state *state = &inst->read_state;
+ if (!inst) {
+ ERROR(PLUGIN_NAME " plugin: NULL userdata");
+ return -1;
+ }
- if (conn == NULL) {
+ if (inst->id == 0 && conn == NULL) {
/* `conn_string == NULL' is acceptable. */
conn = virConnectOpenReadOnly(conn_string);
if (conn == NULL) {
return 0;
}
+static int lv_init_instance(size_t i, plugin_read_cb callback) {
+ struct lv_user_data *lv_ud = &(lv_read_user_data[i]);
+ struct lv_read_instance *inst = &lv_ud->inst;
+
+ memset(lv_ud, 0, sizeof(*lv_ud));
+
+ ssnprintf(inst->tag, sizeof(inst->tag), "%s-%zu", PLUGIN_NAME, i);
+ inst->id = i;
+
+ user_data_t *ud = &lv_ud->ud;
+ ud->data = inst;
+ ud->free_func = NULL;
+
+ INFO(PLUGIN_NAME "plugin: reader %s initialized", inst->tag);
+ return plugin_register_complex_read(NULL, inst->tag, callback, 0, ud);
+}
+
+static int lv_init(void) {
+ if (virInitialize() != 0)
+ return -1;
+
+ for (size_t i = 0; i < nr_instances; ++i)
+ lv_init_instance(i, lv_read);
+
+ return 0;
+}
+
static int refresh_lists(struct lv_read_state *state) {
int n;
}
static int lv_shutdown(void) {
- struct lv_read_state *state = &read_state;
- free_block_devices(state);
- free_interface_devices(state);
- free_domains(state);
+ for (size_t i = 0; i < nr_instances; ++i) {
+ struct lv_read_state *state = &(lv_read_user_data[i].inst.read_state);
+ free_block_devices(state);
+ free_interface_devices(state);
+ free_domains(state);
+ }
if (conn != NULL)
virConnectClose(conn);
void module_register(void) {
plugin_register_config(PLUGIN_NAME, lv_config, config_keys, NR_CONFIG_KEYS);
plugin_register_init(PLUGIN_NAME, lv_init);
- plugin_register_read(PLUGIN_NAME, lv_read);
+ plugin_register_complex_read(NULL, PLUGIN_NAME, lv_read, 0, NULL);
plugin_register_shutdown(PLUGIN_NAME, lv_shutdown);
}