The RRD client library does not provide means to check the status of a
connection and there's no way to detect that the connection is broken after,
for example, the daemon restarted. To work around that, try to reconnect if
any client operation fails.
Reported via https://bugs.debian.org/657877
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)
+ {
+ char *err = rrd_get_error ();
+ ERROR ("rrdcached plugin: Failed to reconnect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, err, 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;
rrdc_stats_t *ptr;
static int rc_read (void)
{
int status;
rrdc_stats_t *head;
rrdc_stats_t *ptr;
value_t values[1];
value_list_t vl = VALUE_LIST_INIT;
value_t values[1];
value_list_t vl = VALUE_LIST_INIT;
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);
+ char *err = rrd_get_error ();
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, err, status);
- head = NULL;
- status = rrdc_stats_get (&head);
- if (status != 0)
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ head = NULL;
+ 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 with status %i.", status);
return (-1);
}
ERROR ("rrdcached plugin: rrdc_stats_get failed with status %i.", status);
return (-1);
}
char values[512];
char *values_array[2];
int status;
char values[512];
char *values_array[2];
int status;
if (daemon_address == NULL)
{
if (daemon_address == NULL)
{
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);
+ char *err = rrd_get_error ();
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, err, status);
- status = rrdc_update (filename, /* values_num = */ 1, (void *) values_array);
- if (status != 0)
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ 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 with "
"status %i.",
filename, values_array[0], status);
ERROR ("rrdcached plugin: rrdc_update (%s, [%s], 1) failed with "
"status %i.",
filename, values_array[0], status);
{
char filename[PATH_MAX + 1];
int status;
{
char filename[PATH_MAX + 1];
int status;
if (identifier == NULL)
return (EINVAL);
if (identifier == NULL)
return (EINVAL);
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);
+ char *err = rrd_get_error ();
+ ERROR ("rrdcached plugin: Failed to connect to RRDCacheD "
+ "at %s: %s (status=%d)", daemon_address, err, status);
- status = rrdc_flush (filename);
- if (status != 0)
+ /* The RRD client lib does not provide any means for checking a
+ * connection, hence we'll have to retry upon failed operations. */
+ 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 with status %i.",
filename, status);
return (-1);
ERROR ("rrdcached plugin: rrdc_flush (%s) failed with status %i.",
filename, status);
return (-1);