LTTngTop working with up-to-date LTTng stack !
authorJulien Desfossez <julien.desfossez@efficios.com>
Wed, 22 Feb 2012 02:47:03 +0000 (21:47 -0500)
committerJulien Desfossez <julien.desfossez@efficios.com>
Wed, 22 Feb 2012 02:47:20 +0000 (21:47 -0500)
No more build dependency on the babeltrace tree.
Perf counters handling redesigned to suit the new API.

Signed-off-by: Julien Desfossez <julien.desfossez@efficios.com>
src/common.c
src/cursesdisplay.c
src/lttngtop.c
src/lttngtoptypes.h

index e59de36c8157ffb6512f6f3a01872978f9fbe098..0d39f303559eeafe729699e5591b54f921e7962b 100644 (file)
@@ -47,7 +47,7 @@ struct processtop* add_proc(struct lttngtop *ctx, int tid, char *comm,
                newproc->birth = timestamp;
                newproc->process_files_table = g_ptr_array_new();
                newproc->threads = g_ptr_array_new();
-               newproc->perf = g_hash_table_new(g_direct_hash, g_direct_equal);
+               newproc->perf = g_hash_table_new(g_str_hash, g_str_equal);
                newproc->iostream = g_new0(struct iostream, 1);
                newproc->iostream->ret_read = 0;
                newproc->iostream->ret_write = 0;
@@ -118,7 +118,7 @@ struct cputime* add_cpu(int cpu)
        newcpu = g_new0(struct cputime, 1);
        newcpu->id = cpu;
        newcpu->current_task = NULL;
-       newcpu->perf = g_hash_table_new(g_direct_hash, g_direct_equal);
+       newcpu->perf = g_hash_table_new(g_str_hash, g_str_equal);
 
        g_ptr_array_add(lttngtop.cpu_table, newcpu);
 
@@ -176,7 +176,7 @@ void copy_perf_counter(gpointer key, gpointer value, gpointer new_table)
        newperf->count = ((struct perfcounter *) value)->count;
        newperf->visible = ((struct perfcounter *) value)->visible;
        newperf->sort = ((struct perfcounter *) value)->sort;
-       g_hash_table_insert((GHashTable *) new_table, key, newperf);
+       g_hash_table_insert((GHashTable *) new_table, strdup(key), newperf);
 }
 
 void rotate_perfcounter() {
@@ -217,7 +217,7 @@ struct lttngtop* get_copy_lttngtop(unsigned long start, unsigned long end)
        dst->process_table = g_ptr_array_new();
        dst->files_table = g_ptr_array_new();
        dst->cpu_table = g_ptr_array_new();
-       dst->perf_list = g_hash_table_new(g_direct_hash, g_direct_equal);
+       dst->perf_list = g_hash_table_new(g_str_hash, g_str_equal);
 
        rotate_cputime(end);
 
@@ -230,17 +230,16 @@ struct lttngtop* get_copy_lttngtop(unsigned long start, unsigned long end)
                new->threads = g_ptr_array_new();
                new->comm = strdup(tmp->comm);
                new->process_files_table = g_ptr_array_new();
-               new->perf = g_hash_table_new(g_direct_hash, g_direct_equal);
+               new->perf = g_hash_table_new(g_str_hash, g_str_equal);
                g_hash_table_foreach(tmp->perf, copy_perf_counter, new->perf);
 
                new->iostream = g_new0(struct iostream, 1);
                memcpy(new->iostream, tmp->iostream, sizeof(struct iostream));
                /* compute the stream speed */
-               if (end - start != 0)
-               {
-                       time = (end - start)/NSEC_PER_SEC;
-                       new->iostream->ret_read = new->iostream->ret_read/(time);
-                       new->iostream->ret_write = new->iostream->ret_write/(time);
+               if (end - start != 0) {
+                       time = (end - start) / NSEC_PER_SEC;
+                       new->iostream->ret_read = new->iostream->ret_read / time;
+                       new->iostream->ret_write = new->iostream->ret_write / time;
                }
 
                for (j = 0; j < tmp->process_files_table->len; j++) {
@@ -272,9 +271,11 @@ struct lttngtop* get_copy_lttngtop(unsigned long start, unsigned long end)
                 */
                if (tmp->death > 0 && tmp->death < end) {
                        g_ptr_array_remove(lttngtop.process_table, tmp);
+                       /* FIXME : TRUE does not mean clears the object in it */
                        g_ptr_array_free(tmp->threads, TRUE);
                        free(tmp->comm);
                        g_ptr_array_free(tmp->process_files_table, TRUE);
+                       /* FIXME : clear elements */
                        g_hash_table_destroy(tmp->perf);
                        g_free(tmp);
                }
@@ -285,7 +286,7 @@ struct lttngtop* get_copy_lttngtop(unsigned long start, unsigned long end)
                tmpcpu = g_ptr_array_index(lttngtop.cpu_table, i);
                newcpu = g_new0(struct cputime, 1);
                memcpy(newcpu, tmpcpu, sizeof(struct cputime));
-               newcpu->perf = g_hash_table_new(g_direct_hash, g_direct_equal);
+               newcpu->perf = g_hash_table_new(g_str_hash, g_str_equal);
                g_hash_table_foreach(tmpcpu->perf, copy_perf_counter, newcpu->perf);
                /*
                 * note : we don't care about the current process pointer in the copy
@@ -293,6 +294,7 @@ struct lttngtop* get_copy_lttngtop(unsigned long start, unsigned long end)
                 */
                g_ptr_array_add(dst->cpu_table, newcpu);
        }
+       /* FIXME : better algo */
        /* create the threads index if required */
        for (i = 0; i < dst->process_table->len; i++) {
                tmp = g_ptr_array_index(dst->process_table, i);
index 0f7948581b800f5c8d062230421f1443c32132f2..8417fdafe293a684ff0d85f6dc8ab7e94280d548 100644 (file)
@@ -453,9 +453,10 @@ void update_perf()
        int header_offset = 2;
        int perf_row = 40;
        struct perfcounter *perfn1, *perfn2;
-       GList *perflist;
        char *perf_key = NULL;
        int value;
+       GHashTableIter iter;
+       gpointer key;
 
        set_window_title(center, "Perf Top");
        wattron(center, A_BOLD);
@@ -464,26 +465,25 @@ void update_perf()
        mvwprintw(center, 1, 22, "NAME");
 
        perf_row = 40;
-       perflist = g_list_first(g_hash_table_get_keys(data->perf_list));
-       while (perflist) {
-               perfn1 = g_hash_table_lookup(data->perf_list, perflist->data);
-               /* + 6 to strip the "_perf_" prefix */
+       g_hash_table_iter_init(&iter, data->perf_list);
+       while (g_hash_table_iter_next (&iter, &key, (gpointer) &perfn1)) {
                if (perfn1->visible) {
+                       /* + 6 to strip the "_perf_" prefix */
                        mvwprintw(center, 1, perf_row, "%s",
-                                       (char *) perflist->data + 6);
+                                       (char *) key + 6);
                        perf_row += 20;
                }
                if (perfn1->sort) {
-                       perf_key = (char *) perflist->data;
+                       perf_key = (char *) key;
                }
-               perflist = g_list_next(perflist);
        }
+
        wattroff(center, A_BOLD);
 
        g_ptr_array_sort_with_data(data->process_table, sort_perf, perf_key);
+
        for (i = 0; i < data->process_table->len && 
                        nblinedisplayed < max_center_lines; i++) {
-               GList *perf_keys;
                tmp = g_ptr_array_index(data->process_table, i);
 
                if (current_line == selected_line) {
@@ -496,24 +496,12 @@ void update_perf()
                mvwprintw(center, current_line + header_offset, 11, "%d", tmp->tid);
                mvwprintw(center, current_line + header_offset, 22, "%s", tmp->comm);
 
-               /* FIXME : sometimes there is a segfault here, I have no idea why :-( */
-               perf_keys = g_hash_table_get_keys(data->perf_list);
-               if (perf_keys)
-                       perflist = g_list_first(perf_keys);
-               else
-                       perflist = NULL;
+               g_hash_table_iter_init(&iter, data->perf_list);
 
                perf_row = 40;
-               j = 0;
-               while (perflist) {
-                       j++;
-                       perfn1 = g_hash_table_lookup(data->perf_list, perflist->data);
-                       if (!perfn1) {
-                               perflist = g_list_next(perflist);
-                               continue;
-                       }
+               while (g_hash_table_iter_next (&iter, &key, (gpointer) &perfn1)) {
                        if (perfn1->visible) {
-                               perfn2 = g_hash_table_lookup(tmp->perf, perflist->data);
+                               perfn2 = g_hash_table_lookup(tmp->perf, (char *) key);
                                if (perfn2)
                                        value = perfn2->count;
                                else
@@ -521,7 +509,6 @@ void update_perf()
                                mvwprintw(center, current_line + header_offset, perf_row, "%d", value);
                                perf_row += 20;
                        }
-                       perflist = g_list_next(perflist);
                }
 
                wattroff(center, COLOR_PAIR(5));
index ad1e7137c5ab5f9a1c7d46de7b8b02622dadc2b0..924864b32fb9f50710717ee7ed07642a8c0ffca6 100644 (file)
@@ -36,6 +36,7 @@
 #include <errno.h>
 #include <sys/types.h>
 #include <fts.h>
+#include <assert.h>
 
 #include "lttngtoptypes.h"
 #include "cputop.h"
@@ -73,6 +74,8 @@ static struct poptOption long_options[] = {
 void *refresh_thread(void *p)
 {
        while (1) {
+               if (quit)
+                       return NULL;
                sem_wait(&pause_sem);
                sem_post(&pause_sem);
                sem_post(&timer);
@@ -93,8 +96,8 @@ void *ncurses_display(void *p)
                sem_wait(&pause_sem);
 
                copy = g_ptr_array_index(copies, current_display_index);
-               if (copy)
-                       display(current_display_index++);
+               assert(copy);
+               display(current_display_index++);
 
                sem_post(&goodtoupdate);
                sem_post(&pause_sem);
@@ -160,7 +163,7 @@ struct perfcounter *get_perf_counter(const char *name, struct processtop *proc,
        ret = g_new0(struct perfcounter, 1);
        /* by default, make it visible in the UI */
        ret->visible = 1;
-       g_hash_table_insert(table, (gpointer) name, ret);
+       g_hash_table_insert(table, (gpointer) strdup(name), ret);
 
        global = g_hash_table_lookup(lttngtop.perf_list, (gpointer) name);
        if (!global) {
@@ -169,7 +172,7 @@ struct perfcounter *get_perf_counter(const char *name, struct processtop *proc,
                /* by default, sort on the first perf context */
                if (g_hash_table_size(lttngtop.perf_list) == 0)
                        global->sort = 1;
-               g_hash_table_insert(lttngtop.perf_list, (gpointer) name, global);
+               g_hash_table_insert(lttngtop.perf_list, (gpointer) strdup(name), global);
        }
 
 end:
@@ -258,7 +261,7 @@ enum bt_cb_ret fix_process_table(struct bt_ctf_event *call_data,
        struct definition *scope;
        unsigned long timestamp;
 
-       /* FIXME : check context pid, tid, ppid and comm */
+       /* FIXME : display nice error when missing context pid, tid, ppid and comm */
 
        timestamp = bt_ctf_get_timestamp(call_data);
        if (timestamp == -1ULL)
@@ -317,7 +320,7 @@ error:
 void init_lttngtop()
 {
        copies = g_ptr_array_new();
-       lttngtop.perf_list = g_hash_table_new(g_direct_hash, g_direct_equal);
+       lttngtop.perf_list = g_hash_table_new(g_str_hash, g_str_equal);
 
        sem_init(&goodtodisplay, 0, 0);
        sem_init(&goodtoupdate, 0, 1);
@@ -564,7 +567,9 @@ int main(int argc, char **argv)
 
        quit = 1;
        pthread_join(display_thread, NULL);
+       pthread_join(timer_thread, NULL);
 
 end:
+       bt_context_put(bt_ctx);
        return 0;
 }
index f10a6841ad2becdc45748b2ca6cbd86778133d34..7030b32f81ae253f871c13638a3f7f07ae399968 100644 (file)
@@ -157,10 +157,10 @@ struct signals {
 };
 
 struct iostream {
-        struct syscalls *syscall_info; /* NULL if there is no waiting for an exit_syscall */
-        unsigned long ret_read;        /* value returned by an I/O syscall_exit for a sys_read*/
-        unsigned long ret_write;       /* value returned by an I/O syscall_exit for a sys_write*/
-        unsigned long ret_total;
+       struct syscalls *syscall_info; /* NULL if there is no waiting for an exit_syscall */
+       unsigned long ret_read;        /* value returned by an I/O syscall_exit for a sys_read*/
+       unsigned long ret_write;       /* value returned by an I/O syscall_exit for a sys_write*/
+       unsigned long ret_total;
 };
 
 #endif /* LTTNGTOPTYPES_H */
This page took 0.039114 seconds and 4 git commands to generate.