]> git.ipfire.org Git - thirdparty/rrdtool-1.x.git/commitdiff
backport of the (C)DEF hash patch to accelerate processing of large (+100 statements...
authorTobias Oetiker <tobi@oetiker.ch>
Tue, 30 Apr 2013 09:28:20 +0000 (11:28 +0200)
committerTobias Oetiker <tobi@oetiker.ch>
Tue, 30 Apr 2013 09:28:20 +0000 (11:28 +0200)
src/rrd_graph.c
src/rrd_graph.h
src/rrd_graph_helper.c

index 8de7ad59af839efad074641728b2d915a9c8e77a..cf923999c7124fe8324c93ad9cbe84708f6359ae 100644 (file)
@@ -317,6 +317,14 @@ int im_free(
     if (im->daemon_addr != NULL)
       free(im->daemon_addr);
 
+    if (im->gdef_map){
+        g_hash_table_destroy(im->gdef_map);        
+    }
+
+    if (im->rrd_map){
+        g_hash_table_destroy(im->rrd_map);        
+    }
+
     for (i = 0; i < (unsigned) im->gdes_c; i++) {
         if (im->gdes[i].data_first) {
             /* careful here, because a single pointer can occur several times */
@@ -821,7 +829,6 @@ int data_fetch(
     image_desc_t *im)
 {
     int       i, ii;
-    int       skip;
 
     /* pull the data from the rrd files ... */
     for (i = 0; i < (int) im->gdes_c; i++) {
@@ -829,33 +836,21 @@ int data_fetch(
         if (im->gdes[i].gf != GF_DEF)
             continue;
 
-        skip = 0;
         /* do we have it already ? */
-        for (ii = 0; ii < i; ii++) {
-            if (im->gdes[ii].gf != GF_DEF)
-                continue;
-            if ((strcmp(im->gdes[i].rrd, im->gdes[ii].rrd) == 0)
-                && (im->gdes[i].cf == im->gdes[ii].cf)
-                && (im->gdes[i].cf_reduce == im->gdes[ii].cf_reduce)
-                && (im->gdes[i].start_orig == im->gdes[ii].start_orig)
-                && (im->gdes[i].end_orig == im->gdes[ii].end_orig)
-                && (im->gdes[i].step_orig == im->gdes[ii].step_orig)) {
-                /* OK, the data is already there.
-                 ** Just copy the header portion
-                 */
-                im->gdes[i].start = im->gdes[ii].start;
-                im->gdes[i].end = im->gdes[ii].end;
-                im->gdes[i].step = im->gdes[ii].step;
-                im->gdes[i].ds_cnt = im->gdes[ii].ds_cnt;
-                im->gdes[i].ds_namv = im->gdes[ii].ds_namv;
-                im->gdes[i].data = im->gdes[ii].data;
-                im->gdes[i].data_first = 0;
-                skip = 1;
-            }
-            if (skip)
-                break;
-        }
-        if (!skip) {
+        gpointer value;
+        char *key = gdes_fetch_key(im->gdes[i]);
+        gboolean ok = g_hash_table_lookup_extended(im->rrd_map,key,NULL,&value);
+        free(key);
+        if (ok){
+            ii = GPOINTER_TO_INT(value);
+            im->gdes[i].start = im->gdes[ii].start;
+            im->gdes[i].end = im->gdes[ii].end;
+            im->gdes[i].step = im->gdes[ii].step;
+            im->gdes[i].ds_cnt = im->gdes[ii].ds_cnt;
+            im->gdes[i].ds_namv = im->gdes[ii].ds_namv;
+            im->gdes[i].data = im->gdes[ii].data;
+            im->gdes[i].data_first = 0;
+        } else {
             unsigned long ft_step = im->gdes[i].step;   /* ft_step will record what we got from fetch */
 
             /* Flush the file if
@@ -950,16 +945,16 @@ long find_var(
     image_desc_t *im,
     char *key)
 {
-    long      ii;
-
-    for (ii = 0; ii < im->gdes_c - 1; ii++) {
-        if ((im->gdes[ii].gf == GF_DEF
-             || im->gdes[ii].gf == GF_VDEF || im->gdes[ii].gf == GF_CDEF)
-            && (strcmp(im->gdes[ii].vname, key) == 0)) {
-            return ii;
-        }
+    long match = -1;
+    gpointer value;
+    gboolean ok = g_hash_table_lookup_extended(im->gdef_map,key,NULL,&value);
+    if (ok){
+        match = GPOINTER_TO_INT(value);
     }
-    return -1;
+
+    /* printf("%s -> %ld\n",key,match); */
+
+    return match;    
 }
 
 /* find the greatest common divisor for all the numbers
@@ -4080,7 +4075,8 @@ void rrd_graph_init(
 #ifdef HAVE_TZSET
     tzset();
 #endif
-
+    im->gdef_map = g_hash_table_new_full(g_str_hash, g_str_equal,g_free,NULL);
+    im->rrd_map = g_hash_table_new_full(g_str_hash, g_str_equal,g_free,NULL);
     im->base = 1000;
     im->daemon_addr = NULL;
     im->draw_x_grid = 1;
index f098380b9223eea576de958f29b6060c20ad849a..18b49a3e8a45f489c3c626dafdabef2130a7ee65 100644 (file)
@@ -46,6 +46,8 @@
 #define FULL_SIZE_MODE     0x200    /* -width and -height indicate the total size of the image */
 #define NO_RRDTOOL_TAG 0x400  /* disable the rrdtool tag */
 
+#define gdes_fetch_key(x)  sprintf_alloc("%s:%d:%d:%d:%d",x.rrd,x.cf,x.cf_reduce,x.start_orig,x.end_orig,x.step_orig)
+
 enum tmt_en { TMT_SECOND = 0, TMT_MINUTE, TMT_HOUR, TMT_DAY,
     TMT_WEEK, TMT_MONTH, TMT_YEAR
 };
@@ -285,6 +287,8 @@ typedef struct image_desc_t {
     PangoLayout *layout; /* the pango layout we use for writing fonts */
     rrd_info_t *grinfo; /* root pointer to extra graph info */
     rrd_info_t *grinfo_current; /* pointing to current entry */
+    GHashTable* gdef_map;  /* a map of all *def gdef entries for quick access */
+    GHashTable* rrd_map;  /* a map of all rrd files in use for gdef entries */
 } image_desc_t;
 
 /* Prototypes */
index 82e78ed9c95d356334a8d61de94e2f26622e0596..f94dd34247c49d56390a313de1864fd7d8ee5fc4 100644 (file)
@@ -1094,7 +1094,7 @@ void rrd_graph_script(
         graph_desc_t *gdp;
         unsigned int eaten = 0;
 
-        if (gdes_alloc(im))
+        if (gdes_alloc(im)) /* gdes_c ++ */
             return;     /* the error string is already set */
         gdp = &im->gdes[im->gdes_c - 1];
 #ifdef DEBUG
@@ -1175,5 +1175,13 @@ void rrd_graph_script(
                           &argv[i][eaten], argv[i]);
             return;
         }
+        char *key = gdes_fetch_key((*gdp));
+        if (gdp->gf == GF_DEF && !g_hash_table_lookup_extended(im->rrd_map,key,NULL,NULL)){
+            g_hash_table_insert(im->gdef_map,g_strdup(key),GINT_TO_POINTER(im->gdes_c-1));
+        } 
+        free(key);
+        if (gdp->gf == GF_DEF || gdp->gf == GF_VDEF || gdp->gf == GF_CDEF){
+            g_hash_table_insert(im->gdef_map,g_strdup(gdp->vname),GINT_TO_POINTER(im->gdes_c-1));
+        }
     }
 }