diff --git a/src/rrdcached.c b/src/rrdcached.c
index 645032cbe189686a707c7e6d34db7343432b8882..0b9040536ecc165f0b9a85ea7bacd1d5866358d6 100644 (file)
--- a/src/rrdcached.c
+++ b/src/rrdcached.c
**/
#include "collectd.h"
**/
#include "collectd.h"
+
#include "plugin.h"
#include "common.h"
#include "utils_rrdcreate.h"
#include "plugin.h"
#include "common.h"
#include "utils_rrdcreate.h"
{
int offset;
int status;
{
int offset;
int status;
- int i;
time_t t;
assert (0 == strcmp (ds->type, vl->type));
time_t t;
assert (0 == strcmp (ds->type, vl->type));
return (-1);
offset = status;
return (-1);
offset = status;
- for (i = 0; i < ds->ds_num; i++)
+ for (size_t i = 0; i < ds->ds_num; i++)
{
if ((ds->ds[i].type != DS_TYPE_COUNTER)
&& (ds->ds[i].type != DS_TYPE_GAUGE)
{
if ((ds->ds[i].type != DS_TYPE_COUNTER)
&& (ds->ds[i].type != DS_TYPE_GAUGE)
status = ssnprintf (buffer + offset, buffer_len - offset,
":%llu", vl->values[i].counter);
}
status = ssnprintf (buffer + offset, buffer_len - offset,
":%llu", vl->values[i].counter);
}
- else if (ds->ds[i].type == DS_TYPE_GAUGE)
+ else if (ds->ds[i].type == DS_TYPE_GAUGE)
{
status = ssnprintf (buffer + offset, buffer_len - offset,
":%f", vl->values[i].gauge);
{
status = ssnprintf (buffer + offset, buffer_len - offset,
":%f", vl->values[i].gauge);
else /* if (ds->ds[i].type == DS_TYPE_ABSOLUTE) */ {
status = ssnprintf (buffer + offset, buffer_len - offset,
":%"PRIu64, vl->values[i].absolute);
else /* if (ds->ds[i].type == DS_TYPE_ABSOLUTE) */ {
status = ssnprintf (buffer + offset, buffer_len - offset,
":%"PRIu64, vl->values[i].absolute);
-
+
}
if ((status < 1) || (status >= (buffer_len - offset)))
}
if ((status < 1) || (status >= (buffer_len - offset)))
static int rc_config (oconfig_item_t *ci)
{
static int rc_config (oconfig_item_t *ci)
{
- int i;
-
- for (i = 0; i < ci->children_num; i++)
+ for (int i = 0; i < ci->children_num; i++)
{
oconfig_item_t const *child = ci->children + i;
const char *key = child->key;
{
oconfig_item_t const *child = ci->children + i;
const char *key = child->key;
return (0);
} /* int rc_config */
return (0);
} /* int rc_config */
+static int try_reconnect (void)
+{
+ int status;
+
+ rrdc_disconnect ();
+
+ rrd_clear_error ();
+ status = rrdc_connect (daemon_address);
+ if (status != 0)
+ {
+ ERROR ("rrdcached plugin: Failed to reconnect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, rrd_get_error (), status);
+ return (-1);
+ }
+
+ INFO ("rrdcached plugin: Successfully reconnected to RRDCacheD "
+ "at %s", daemon_address);
+ return (0);
+} /* int try_reconnect */
+
static int rc_read (void)
{
int status;
rrdc_stats_t *head;
static int rc_read (void)
{
int status;
rrdc_stats_t *head;
- rrdc_stats_t *ptr;
+ _Bool retried = 0;
value_t values[1];
value_list_t vl = VALUE_LIST_INIT;
value_t values[1];
value_list_t vl = VALUE_LIST_INIT;
sstrncpy (vl.host, daemon_address, sizeof (vl.host));
sstrncpy (vl.plugin, "rrdcached", sizeof (vl.plugin));
sstrncpy (vl.host, daemon_address, sizeof (vl.host));
sstrncpy (vl.plugin, "rrdcached", sizeof (vl.plugin));
+ rrd_clear_error ();
status = rrdc_connect (daemon_address);
if (status != 0)
{
status = rrdc_connect (daemon_address);
if (status != 0)
{
- ERROR ("rrdcached plugin: rrdc_connect (%s) failed with status %i.",
- daemon_address, status);
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, rrd_get_error (), status);
return (-1);
}
return (-1);
}
- head = NULL;
- status = rrdc_stats_get (&head);
- if (status != 0)
+ while (42)
{
{
- ERROR ("rrdcached plugin: rrdc_stats_get failed with status %i.", status);
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ head = NULL;
+ rrd_clear_error ();
+ status = rrdc_stats_get (&head);
+ if (status == 0)
+ break;
+
+ if (!retried)
+ {
+ retried = 1;
+ if (try_reconnect () == 0)
+ continue;
+ /* else: report the error and fail */
+ }
+
+ ERROR ("rrdcached plugin: rrdc_stats_get failed: %s (status=%i).",
+ rrd_get_error (), status);
return (-1);
}
return (-1);
}
- for (ptr = head; ptr != NULL; ptr = ptr->next)
+ for (rrdc_stats_t *ptr = head; ptr != NULL; ptr = ptr->next)
{
if (ptr->type == RRDC_STATS_TYPE_GAUGE)
values[0].gauge = (gauge_t) ptr->value.gauge;
{
if (ptr->type == RRDC_STATS_TYPE_GAUGE)
values[0].gauge = (gauge_t) ptr->value.gauge;
char values[512];
char *values_array[2];
int status;
char values[512];
char *values_array[2];
int status;
+ _Bool retried = 0;
if (daemon_address == NULL)
{
if (daemon_address == NULL)
{
}
}
}
}
+ rrd_clear_error ();
status = rrdc_connect (daemon_address);
if (status != 0)
{
status = rrdc_connect (daemon_address);
if (status != 0)
{
- ERROR ("rrdcached plugin: rrdc_connect (%s) failed with status %i.",
- daemon_address, status);
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, rrd_get_error (), status);
return (-1);
}
return (-1);
}
- status = rrdc_update (filename, /* values_num = */ 1, (void *) values_array);
- if (status != 0)
+ while (42)
{
{
- ERROR ("rrdcached plugin: rrdc_update (%s, [%s], 1) failed with "
- "status %i.",
- filename, values_array[0], status);
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ rrd_clear_error ();
+ status = rrdc_update (filename, /* values_num = */ 1, (void *) values_array);
+ if (status == 0)
+ break;
+
+ if (!retried)
+ {
+ retried = 1;
+ if (try_reconnect () == 0)
+ continue;
+ /* else: report the error and fail */
+ }
+
+ ERROR ("rrdcached plugin: rrdc_update (%s, [%s], 1) failed: %s (status=%i)",
+ filename, values_array[0], rrd_get_error (), status);
return (-1);
}
return (-1);
}
{
char filename[PATH_MAX + 1];
int status;
{
char filename[PATH_MAX + 1];
int status;
+ _Bool retried = 0;
if (identifier == NULL)
return (EINVAL);
if (identifier == NULL)
return (EINVAL);
else
ssnprintf (filename, sizeof (filename), "%s.rrd", identifier);
else
ssnprintf (filename, sizeof (filename), "%s.rrd", identifier);
+ rrd_clear_error ();
status = rrdc_connect (daemon_address);
if (status != 0)
{
status = rrdc_connect (daemon_address);
if (status != 0)
{
- ERROR ("rrdcached plugin: rrdc_connect (%s) failed with status %i.",
- daemon_address, status);
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, rrd_get_error (), status);
return (-1);
}
return (-1);
}
- status = rrdc_flush (filename);
- if (status != 0)
+ while (42)
{
{
- ERROR ("rrdcached plugin: rrdc_flush (%s) failed with status %i.",
- filename, status);
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ rrd_clear_error ();
+ status = rrdc_flush (filename);
+ if (status == 0)
+ break;
+
+ if (!retried)
+ {
+ retried = 1;
+ if (try_reconnect () == 0)
+ continue;
+ /* else: report the error and fail */
+ }
+
+ ERROR ("rrdcached plugin: rrdc_flush (%s) failed: %s (status=%i).",
+ filename, rrd_get_error (), status);
return (-1);
}
DEBUG ("rrdcached plugin: rrdc_flush (%s): Success.", filename);
return (-1);
}
DEBUG ("rrdcached plugin: rrdc_flush (%s): Success.", filename);