src/rrd_daemon.c: Updated the enqueueing function to provide insertion at the head.
[rrdtool.git] / src / rrd_daemon.c
index df31d51..7423088 100644 (file)
@@ -116,6 +116,13 @@ struct cache_item_s
   cache_item_t *next;
 };
 
+enum queue_side_e
+{
+  HEAD,
+  TAIL
+};
+typedef enum queue_side_e queue_side_t;
+
 /*
  * Variables
  */
@@ -160,7 +167,8 @@ static void sig_term_handler (int s __attribute__((unused))) /* {{{ */
  * enqueue_cache_item:
  * `cache_lock' must be acquired before calling this function!
  */
-static int enqueue_cache_item (cache_item_t *ci) /* {{{ */
+static int enqueue_cache_item (cache_item_t *ci, /* {{{ */
+    queue_side_t side)
 {
   RRDD_LOG (LOG_DEBUG, "enqueue_cache_item: Adding %s to the update queue.",
       ci->file);
@@ -168,21 +176,58 @@ static int enqueue_cache_item (cache_item_t *ci) /* {{{ */
   if (ci == NULL)
     return (-1);
 
-  if ((ci->flags & CI_FLAGS_IN_QUEUE) != 0)
-    return (-1);
-
-  assert (ci->next == NULL);
-
   if (ci->values_num == 0)
     return (0);
 
-  if (cache_queue_tail == NULL)
-    cache_queue_head = ci;
-  else
-    cache_queue_tail->next = ci;
-  cache_queue_tail = ci;
+  if (side == HEAD)
+  {
+    if ((ci->flags & CI_FLAGS_IN_QUEUE) == 0)
+    {
+      assert (ci->next == NULL);
+      ci->next = cache_queue_head;
+      cache_queue_head = ci;
 
-  ci->flags |= CI_FLAGS_IN_QUEUE;
+      if (cache_queue_tail == NULL)
+        cache_queue_tail = cache_queue_head;
+    }
+    else if (cache_queue_head == ci)
+    {
+      /* do nothing */
+    }
+    else /* enqueued, but not first entry */
+    {
+      cache_item_t *prev;
+
+      /* find previous entry */
+      for (prev = cache_queue_head; prev != NULL; prev = prev->next)
+        if (prev->next == ci)
+          break;
+      assert (prev != NULL);
+
+      /* move to the front */
+      prev->next = ci->next;
+      ci->next = cache_queue_head;
+      cache_queue_head = ci;
+
+      /* check if we need to adapt the tail */
+      if (cache_queue_tail == ci)
+        cache_queue_tail = prev;
+    }
+  }
+  else /* (side == TAIL) */
+  {
+    /* We don't move values back in the list.. */
+    if ((ci->flags & CI_FLAGS_IN_QUEUE) != 0)
+      return (0);
+
+    assert (ci->next == NULL);
+
+    if (cache_queue_tail == NULL)
+      cache_queue_head = ci;
+    else
+      cache_queue_tail->next = ci;
+    cache_queue_tail = ci;
+  }
 
   ci->flags |= CI_FLAGS_IN_QUEUE;
 
@@ -208,7 +253,7 @@ static gboolean tree_callback_flush (gpointer key /* {{{ */
   if (((now - ci->last_flush_time) >= config_write_interval)
       && ((ci->flags & CI_FLAGS_IN_QUEUE) == 0)
       && (ci->values_num > 0))
-    enqueue_cache_item (ci);
+    enqueue_cache_item (ci, TAIL);
 
   return (TRUE);
 } /* }}} gboolean tree_callback_flush */
@@ -470,7 +515,7 @@ static int handle_request_update (int fd, /* {{{ */
       && ((ci->flags & CI_FLAGS_IN_QUEUE) == 0)
       && (ci->values_num > 0))
   {
-    enqueue_cache_item (ci);
+    enqueue_cache_item (ci, TAIL);
     pthread_cond_signal (&cache_cond);
   }
 
@@ -949,7 +994,7 @@ static int daemonize (void) /* {{{ */
     sigaction (SIGPIPE, &sa, NULL);
   }
 
-  openlog ("rrdd", LOG_PID, LOG_DAEMON);
+  openlog ("rrdcached", LOG_PID, LOG_DAEMON);
 
   cache_tree = g_tree_new ((GCompareFunc) strcmp);
   if (cache_tree == NULL)
@@ -1052,7 +1097,7 @@ static int read_options (int argc, char **argv) /* {{{ */
       case '?':
         printf ("RRDd %s  Copyright (C) 2008 Florian octo Forster\n"
             "\n"
-            "Usage: rrdd [options]\n"
+            "Usage: rrdcached [options]\n"
             "\n"
             "Valid options are:\n"
             "  -l <address>  Socket address to listen to.\n"
@@ -1061,7 +1106,7 @@ static int read_options (int argc, char **argv) /* {{{ */
             "\n"
             "For more information and a detailed description of all options "
             "please refer\n"
-            "to the rrdd(1) manual page.\n",
+            "to the rrdcached(1) manual page.\n",
             VERSION);
         status = -1;
         break;