From: Julien Desfossez Date: Thu, 23 Aug 2012 21:11:35 +0000 (-0400) Subject: lttng_statedump_process_state for each PID NS X-Git-Tag: v2.1.0-rc1~7 X-Git-Url: http://git.lttng.org/?p=lttng-modules.git;a=commitdiff_plain;h=73e8ba371039bc05745a739db4d69b4220a1c03e lttng_statedump_process_state for each PID NS When a process is in a namespace, its pid, tid and ppid are relative to the namespace. Since namespaces can be nested, we need to know the representation of each process in each namespace. This patch changes the lttng_enumerate_task_fd to iterate over each PID namespace of a process if any, that way we generate, in the statedump, an entry for each process in each namespace it belongs. To know the nesting level, the field "level" is added to the lttng_statedump_process_state event, 0 being the top-level. For processes running on the top-level namespace, the statedump behaviour is unchanged (except the added "level" field). For example (no nesting, just one level of namespace) : lttng_statedump_process_state: { tid = 32185, vtid = 1, pid = 32185, vpid = 1, ppid = 32173, vppid = 0, level = 1, name = "init" } lttng_statedump_process_state: { tid = 32185, vtid = 32185, pid = 32185, vpid = 32185, ppid = 32173, vppid = 32173, level = 0, name = "init" } Confirmed that the process 32173 in the top-level namespace is indeed the lxc-start command that created the container and its namespace. [ Edit by Mathieu Desnoyers: Minor cleanups ] Signed-off-by: Julien Desfossez Signed-off-by: Mathieu Desnoyers --- diff --git a/instrumentation/events/lttng-module/lttng-statedump.h b/instrumentation/events/lttng-module/lttng-statedump.h index 5fc15a88..ea0b6d9d 100644 --- a/instrumentation/events/lttng-module/lttng-statedump.h +++ b/instrumentation/events/lttng-module/lttng-statedump.h @@ -6,6 +6,7 @@ #include #include +#include TRACE_EVENT(lttng_statedump_start, TP_PROTO(struct lttng_session *session), @@ -30,8 +31,9 @@ TRACE_EVENT(lttng_statedump_end, TRACE_EVENT(lttng_statedump_process_state, TP_PROTO(struct lttng_session *session, struct task_struct *p, - int type, int mode, int submode, int status), - TP_ARGS(session, p, type, mode, submode, status), + int type, int mode, int submode, int status, + struct pid_namespace *pid_ns), + TP_ARGS(session, p, type, mode, submode, status, pid_ns), TP_STRUCT__entry( __field(pid_t, tid) __field(pid_t, vtid) @@ -44,38 +46,13 @@ TRACE_EVENT(lttng_statedump_process_state, __field(int, mode) __field(int, submode) __field(int, status) + __field(int, ns_level) ), TP_fast_assign( tp_assign(tid, p->pid) - tp_assign(vtid, - ({ - struct nsproxy *proxy; - pid_t ret = 0; - - rcu_read_lock(); - proxy = task_nsproxy(p); - if (proxy) { - ret = task_pid_nr_ns(p, - proxy->pid_ns); - } - rcu_read_unlock(); - ret; - })) + tp_assign(vtid, pid_ns ? task_pid_nr_ns(p, pid_ns) : 0) tp_assign(pid, p->tgid) - tp_assign(vpid, - ({ - struct nsproxy *proxy; - pid_t ret = 0; - - rcu_read_lock(); - proxy = task_nsproxy(p); - if (proxy) { - ret = task_tgid_nr_ns(p, - proxy->pid_ns); - } - rcu_read_unlock(); - ret; - })) + tp_assign(vpid, pid_ns ? task_tgid_nr_ns(p, pid_ns) : 0) tp_assign(ppid, ({ pid_t ret; @@ -88,16 +65,11 @@ TRACE_EVENT(lttng_statedump_process_state, tp_assign(vppid, ({ struct task_struct *parent; - struct nsproxy *proxy; pid_t ret = 0; rcu_read_lock(); parent = rcu_dereference(p->real_parent); - proxy = task_nsproxy(parent); - if (proxy) { - ret = task_tgid_nr_ns(parent, - proxy->pid_ns); - } + ret = task_tgid_nr_ns(parent, pid_ns); rcu_read_unlock(); ret; })) @@ -106,6 +78,7 @@ TRACE_EVENT(lttng_statedump_process_state, tp_assign(mode, mode) tp_assign(submode, submode) tp_assign(status, status) + tp_assign(ns_level, pid_ns ? pid_ns->level : 0) ), TP_printk("") ) diff --git a/lttng-statedump-impl.c b/lttng-statedump-impl.c index e042a96d..89b55e53 100644 --- a/lttng-statedump-impl.c +++ b/lttng-statedump-impl.c @@ -272,6 +272,32 @@ void list_interrupts(struct lttng_session *session) } #endif +static +void lttng_statedump_process_ns(struct lttng_session *session, + struct task_struct *p, + enum lttng_thread_type type, + enum lttng_execution_mode mode, + enum lttng_execution_submode submode, + enum lttng_process_status status) +{ + struct nsproxy *proxy; + struct pid_namespace *pid_ns; + + rcu_read_lock(); + proxy = task_nsproxy(p); + if (proxy) { + pid_ns = proxy->pid_ns; + do { + trace_lttng_statedump_process_state(session, + p, type, mode, submode, status, pid_ns); + } while (pid_ns); + } else { + trace_lttng_statedump_process_state(session, + p, type, mode, submode, status, NULL); + } + rcu_read_unlock(); +} + static int lttng_enumerate_process_states(struct lttng_session *session) { @@ -321,7 +347,7 @@ int lttng_enumerate_process_states(struct lttng_session *session) type = LTTNG_USER_THREAD; else type = LTTNG_KERNEL_THREAD; - trace_lttng_statedump_process_state(session, + lttng_statedump_process_ns(session, p, type, mode, submode, status); task_unlock(p); } while_each_thread(g, p);