strlist: Introduce strlist__entry and strlist__nr_entries methods
authorArnaldo Carvalho de Melo <acme@redhat.com>
Sat, 11 Jul 2009 15:18:34 +0000 (12:18 -0300)
committerIngo Molnar <mingo@elte.hu>
Sat, 11 Jul 2009 17:20:25 +0000 (19:20 +0200)
The strlist__entry method allows accessing strlists like an
array, will be used in the 'perf report' to access the first
entry.

We now keep the nr_entries so that we can check if we have just
one entry, will be used in 'perf report' to improve the output
by showing just at the top when we have just, say, one DSO.

While at it use nr_entries to optimize strlist__is_empty by not
using the far more costly rb_first based implementation.

Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
LKML-Reference: <1247325517-12272-2-git-send-email-acme@redhat.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
tools/perf/util/strlist.c
tools/perf/util/strlist.h

index 025a78edfffe72c11aa421abcc2d3ab252dd7d99..7ad38171dc2b9c6a6fb7c8474a1faf24101443cc 100644 (file)
@@ -64,6 +64,7 @@ int strlist__add(struct strlist *self, const char *new_entry)
 
        rb_link_node(&sn->rb_node, parent, p);
        rb_insert_color(&sn->rb_node, &self->entries);
+       ++self->nr_entries;
 
        return 0;
 }
@@ -155,8 +156,9 @@ struct strlist *strlist__new(bool dupstr, const char *slist)
        struct strlist *self = malloc(sizeof(*self));
 
        if (self != NULL) {
-               self->entries = RB_ROOT;
-               self->dupstr = dupstr;
+               self->entries    = RB_ROOT;
+               self->dupstr     = dupstr;
+               self->nr_entries = 0;
                if (slist && strlist__parse_list(self, slist) != 0)
                        goto out_error;
        }
@@ -182,3 +184,17 @@ void strlist__delete(struct strlist *self)
                free(self);
        }
 }
+
+struct str_node *strlist__entry(const struct strlist *self, unsigned int idx)
+{
+       struct rb_node *nd;
+
+       for (nd = rb_first(&self->entries); nd; nd = rb_next(nd)) {
+               struct str_node *pos = rb_entry(nd, struct str_node, rb_node);
+
+               if (!idx--)
+                       return pos;
+       }
+
+       return NULL;
+}
index 2fdcfee87586ab47d69f49cc5ceaf2d71aceadc6..921818e44a542e9aa1f8398d950121cb39fb5c24 100644 (file)
@@ -11,7 +11,8 @@ struct str_node {
 
 struct strlist {
        struct rb_root entries;
-       bool dupstr;
+       unsigned int   nr_entries;
+       bool           dupstr;
 };
 
 struct strlist *strlist__new(bool dupstr, const char *slist);
@@ -21,11 +22,17 @@ void strlist__remove(struct strlist *self, struct str_node *sn);
 int strlist__load(struct strlist *self, const char *filename);
 int strlist__add(struct strlist *self, const char *str);
 
+struct str_node *strlist__entry(const struct strlist *self, unsigned int idx);
 bool strlist__has_entry(struct strlist *self, const char *entry);
 
 static inline bool strlist__empty(const struct strlist *self)
 {
-       return rb_first(&self->entries) == NULL;
+       return self->nr_entries == 0;
+}
+
+static inline unsigned int strlist__nr_entries(const struct strlist *self)
+{
+       return self->nr_entries;
 }
 
 int strlist__parse_list(struct strlist *self, const char *s);