Fix state.c handling of state dump thread state
authorMathieu Desnoyers <mathieu.desnoyers@efficios.com>
Tue, 15 Mar 2011 00:30:55 +0000 (20:30 -0400)
committerMathieu Desnoyers <mathieu.desnoyers@efficios.com>
Tue, 15 Mar 2011 00:30:55 +0000 (20:30 -0400)
Introduce the states:

LTTV_STATE_MAYBE_USER_MODE
LTTV_STATE_MAYBE_SYSCALL
LTTV_STATE_MAYBE_TRAP

tagged by the state dump, and then checked by the fixup perform at statedump
end. The controlflow view shows "unknown" state when these states are seen, but
the fixup knows that it is safe to flag the states as "USER_MODE" and "SYSCALL"
after quiescent state has been reached.

Note that we might incorrectly assign "MAYBE_SYSCALL", and then "SYSCALL" to a
thread preempted in TRAP mode. We should find a way to add instrumentation to
the kernel so the state dump tells us how to differ between these two modes.

Signed-off-by: Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
lttv/lttv/state.c
lttv/lttv/state.h
lttv/modules/gui/controlflow/eventhooks.c

index e98275e8cdf4a488ab198830883c7dc62fa8a04d..475c2305b6e7b2654d54061e3af42b12eba7f218 100644 (file)
@@ -143,8 +143,11 @@ GQuark
 LttvExecutionMode
        LTTV_STATE_MODE_UNKNOWN,
        LTTV_STATE_USER_MODE,
+       LTTV_STATE_MAYBE_USER_MODE,
        LTTV_STATE_SYSCALL,
+       LTTV_STATE_MAYBE_SYSCALL,
        LTTV_STATE_TRAP,
+       LTTV_STATE_MAYBE_TRAP,
        LTTV_STATE_IRQ,
        LTTV_STATE_SOFT_IRQ;
 
@@ -3016,8 +3019,11 @@ static gboolean schedchange(void *hook_data, void *call_data)
                if(process->pid == 0
                        && process->state->t == LTTV_STATE_MODE_UNKNOWN) {
                        if(pid_out == 0) {
-                               /* Scheduling out of pid 0 at beginning of the trace :
-                                * we know for sure it is in syscall mode at this point. */
+                               /*
+                                * Scheduling out of pid 0 at beginning of the trace.
+                                * We are typically in system call mode at this point although
+                                * (FIXME) we might be in a trap handler.
+                                */
                                g_assert(process->execution_stack->len == 1);
                                process->state->t = LTTV_STATE_SYSCALL;
                                process->state->s = LTTV_STATE_WAIT;
@@ -3363,7 +3369,7 @@ static void fix_process(gpointer key, gpointer value, gpointer user_data)
 
        if(process->type == LTTV_STATE_KERNEL_THREAD) {
                es = &g_array_index(process->execution_stack, LttvExecutionState, 0);
-               if(es->t == LTTV_STATE_MODE_UNKNOWN) {
+               if(es->t == LTTV_STATE_MAYBE_SYSCALL) {
                        es->t = LTTV_STATE_SYSCALL;
                        es->n = LTTV_STATE_SUBMODE_NONE;
                        es->entry = *timestamp;
@@ -3374,7 +3380,7 @@ static void fix_process(gpointer key, gpointer value, gpointer user_data)
                }
        } else {
                es = &g_array_index(process->execution_stack, LttvExecutionState, 0);
-               if(es->t == LTTV_STATE_MODE_UNKNOWN) {
+               if(es->t == LTTV_STATE_MAYBE_USER_MODE) {
                        es->t = LTTV_STATE_USER_MODE;
                        es->n = LTTV_STATE_SUBMODE_NONE;
                        es->entry = *timestamp;
@@ -3520,14 +3526,11 @@ static gboolean enum_process_state(void *hook_data, void *call_data)
                                es = process->state = &g_array_index(process->execution_stack,
                                                LttvExecutionState, 0);
                                process->type = LTTV_STATE_KERNEL_THREAD;
-                               es->t = LTTV_STATE_MODE_UNKNOWN;
+                               es->t = LTTV_STATE_MAYBE_SYSCALL;
                                es->s = LTTV_STATE_UNNAMED;
                                es->n = LTTV_STATE_SUBMODE_UNKNOWN;
-#if 0
-                               es->t = LTTV_STATE_SYSCALL;
-                               es->s = status;
-                               es->n = submode;
-#endif //0
+                               //es->s = status;
+                               //es->n = submode;
                        } else {
                                /* User space process :
                                 * bottom : user mode
@@ -3545,14 +3548,11 @@ static gboolean enum_process_state(void *hook_data, void *call_data)
                                process->execution_stack = g_array_set_size(process->execution_stack, 1);
                                es = process->state = &g_array_index(process->execution_stack,
                                                LttvExecutionState, 0);
-                               es->t = LTTV_STATE_MODE_UNKNOWN;
+                               es->t = LTTV_STATE_MAYBE_USER_MODE;
                                es->s = LTTV_STATE_UNNAMED;
                                es->n = LTTV_STATE_SUBMODE_UNKNOWN;
-       #if 0
-                               es->t = LTTV_STATE_USER_MODE;
-                               es->s = status;
-                               es->n = submode;
-       #endif //0
+                               //es->s = status;
+                               //es->n = submode;
                        }
        #if 0
                        /* UNKNOWN STATE */
@@ -4436,8 +4436,11 @@ static void module_init()
        LTTV_STATE_UNBRANDED = g_quark_from_string("");
        LTTV_STATE_MODE_UNKNOWN = g_quark_from_string("MODE_UNKNOWN");
        LTTV_STATE_USER_MODE = g_quark_from_string("USER_MODE");
+       LTTV_STATE_MAYBE_USER_MODE = g_quark_from_string("MAYBE_USER_MODE");
        LTTV_STATE_SYSCALL = g_quark_from_string("SYSCALL");
+       LTTV_STATE_MAYBE_SYSCALL = g_quark_from_string("MAYBE_SYSCALL");
        LTTV_STATE_TRAP = g_quark_from_string("TRAP");
+       LTTV_STATE_MAYBE_TRAP = g_quark_from_string("MAYBE_TRAP");
        LTTV_STATE_IRQ = g_quark_from_string("IRQ");
        LTTV_STATE_SOFT_IRQ = g_quark_from_string("SOFTIRQ");
        LTTV_STATE_SUBMODE_UNKNOWN = g_quark_from_string("UNKNOWN");
index f6793ebeb3ebdc4d5e5853afb13770fa8ff2aeff..3f5ca849b8895aa274f50bc48e7ef7a872f3e7fc 100644 (file)
@@ -192,8 +192,11 @@ typedef GQuark LttvExecutionMode;
 
 extern LttvExecutionMode
        LTTV_STATE_USER_MODE,
+       LTTV_STATE_MAYBE_USER_MODE,
        LTTV_STATE_SYSCALL,
+       LTTV_STATE_MAYBE_SYSCALL,
        LTTV_STATE_TRAP,
+       LTTV_STATE_MAYBE_TRAP,  /* TODO */
        LTTV_STATE_IRQ,
        LTTV_STATE_SOFT_IRQ,
        LTTV_STATE_MODE_UNKNOWN;
index ff056aced7c892edd70e97429d8eddbb6eaf981b..5066b524f7d877cf64b3c9aaee3e20e79d874800 100644 (file)
@@ -245,6 +245,12 @@ static inline PropertiesLine prepare_s_e_line(LttvProcessState *process)
       prop_line.color = drawing_colors[COL_RUN_IRQ];
     else if(process->state->t == LTTV_STATE_SOFT_IRQ)
       prop_line.color = drawing_colors[COL_RUN_SOFT_IRQ];
+    else if(process->state->t == LTTV_STATE_MAYBE_SYSCALL)
+      prop_line.color = drawing_colors[COL_MODE_UNKNOWN];
+    else if(process->state->t == LTTV_STATE_MAYBE_USER_MODE)
+      prop_line.color = drawing_colors[COL_MODE_UNKNOWN];
+    else if(process->state->t == LTTV_STATE_MAYBE_TRAP)
+      prop_line.color = drawing_colors[COL_MODE_UNKNOWN];
     else if(process->state->t == LTTV_STATE_MODE_UNKNOWN)
       prop_line.color = drawing_colors[COL_MODE_UNKNOWN];
     else
This page took 0.027144 seconds and 4 git commands to generate.