graph: drop more than 1 entry, if we are more than 1 above the limit
[fio.git] / graph.c
diff --git a/graph.c b/graph.c
index de65055b99c1ffbb0dc00c88b805629c9bfd5bc9..9eae72722542cf7e4d477db49319562c281aa259 100644 (file)
--- a/graph.c
+++ b/graph.c
@@ -55,6 +55,7 @@ struct graph {
        char *xtitle;
        char *ytitle;
        unsigned int xdim, ydim;
+       double xoffset, yoffset;
        struct graph_label *labels;
        struct graph_label *tail;
        int per_label_limit;
@@ -69,6 +70,12 @@ void graph_set_size(struct graph *g, unsigned int xdim, unsigned int ydim)
        g->ydim = ydim;
 }
 
+void graph_set_position(struct graph *g, double xoffset, double yoffset)
+{
+       g->xoffset = xoffset;
+       g->yoffset = yoffset;
+}
+
 struct graph *graph_new(unsigned int xdim, unsigned int ydim, const char *font)
 {
        struct graph *g;
@@ -397,6 +404,7 @@ void bar_graph_draw(struct graph *bg, cairo_t *cr)
        struct graph_label *lb;
 
        cairo_save(cr);
+       cairo_translate(cr, bg->xoffset, bg->yoffset);
        graph_draw_common(bg, cr, &x1, &y1, &x2, &y2);
 
        nlabels = count_labels(bg->labels);
@@ -473,6 +481,7 @@ void line_graph_draw(struct graph *g, cairo_t *cr)
        int good_data = 1, first = 1;
 
        cairo_save(cr);
+       cairo_translate(cr, g->xoffset, g->yoffset);
        graph_draw_common(g, cr, &x1, &y1, &x2, &y2);
 
        minx = find_xy_value(g, getx, mindouble);
@@ -591,11 +600,24 @@ static void graph_label_add_value(struct graph_label *i, void *value)
 
        if (i->parent->per_label_limit != -1 &&
                i->value_count > i->parent->per_label_limit) {
-               x = i->values;
-               i->values = i->values->next;
-               free(x->value);
-               free(x);
-               i->value_count--;
+               int to_drop = 1;
+
+               /*
+                * If the limit was dynamically reduced, making us more
+                * than 1 entry ahead after adding this one, drop two
+                * entries. This will make us (eventually) reach the
+                * specified limit.
+                */
+               if (i->value_count - i->parent->per_label_limit >= 2)
+                       to_drop = 2;
+
+               while (to_drop--) {
+                       x = i->values;
+                       i->values = i->values->next;
+                       free(x->value);
+                       free(x);
+                       i->value_count--;
+               }
        }
 }