From: Mathieu Desnoyers Date: Sat, 30 Mar 2013 00:47:25 +0000 (-0400) Subject: workqueue instrumentation: remove duplicated structures X-Git-Tag: v2.2.0-rc1~6 X-Git-Url: http://git.liburcu.org/?p=lttng-modules.git;a=commitdiff_plain;h=20008d8c6a4cc7434753c5c34b90b4712f1e94af workqueue instrumentation: remove duplicated structures Don't replicate internal structures from the kernel: this is asking for serious trouble, and could lead to breakage if building on newer kernels that have modified structures. The proper approach, if we really need to extract this information, would be to add APIs to the Linux kernel workqueue that allow getting this information. Signed-off-by: Mathieu Desnoyers --- diff --git a/instrumentation/events/lttng-module/workqueue.h b/instrumentation/events/lttng-module/workqueue.h index 02115c7a..96aa240e 100644 --- a/instrumentation/events/lttng-module/workqueue.h +++ b/instrumentation/events/lttng-module/workqueue.h @@ -16,102 +16,6 @@ struct worker; struct global_cwq; -/* Have to duplicate all these definitions from kernel/workqueue.c */ -/* Extracts only */ - -enum { -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)) - NR_WORKER_POOLS = 2, /* # worker pools per gcwq */ -#endif - BUSY_WORKER_HASH_ORDER = 6, /* 64 pointers */ - BUSY_WORKER_HASH_SIZE = 1 << BUSY_WORKER_HASH_ORDER, -}; - -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)) -struct worker_pool { - struct global_cwq *gcwq; /* I: the owning gcwq */ - unsigned int flags; /* X: flags */ - - struct list_head worklist; /* L: list of pending works */ - int nr_workers; /* L: total number of workers */ - int nr_idle; /* L: currently idle ones */ - - struct list_head idle_list; /* X: list of idle workers */ - struct timer_list idle_timer; /* L: worker idle timeout */ - struct timer_list mayday_timer; /* L: SOS timer for workers */ - -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,7,0)) - struct mutex assoc_mutex; /* protect GCWQ_DISASSOCUATED */ -#else - struct mutex manager_mutex; /* mutex manager should hold */ -#endif - struct ida worker_ida; /* L: for worker IDs */ -}; - -struct global_cwq { - spinlock_t lock; /* the gcwq lock */ - unsigned int cpu; /* I: the associated cpu */ - unsigned int flags; /* L: GCWQ_* flags */ - - /* workers are chained either in busy_hash or pool idle_list */ - struct hlist_head busy_hash[BUSY_WORKER_HASH_SIZE]; - /* L: hash of busy workers */ - -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,7,0)) - struct worker_pool pools[NR_WORKER_POOLS]; - /* normal and highpri pools */ -#else - struct worker_pool pools[2]; /* normal and highpri pools */ - - wait_queue_head_t rebind_hold; /* rebind hold wait */ -#endif -} ____cacheline_aligned_in_smp; - -#else - -struct global_cwq { - spinlock_t lock; /* the gcwq lock */ - struct list_head worklist; /* L: list of pending works */ - unsigned int cpu; /* I: the associated cpu */ - unsigned int flags; /* L: GCWQ_* flags */ - - int nr_workers; /* L: total number of workers */ - int nr_idle; /* L: currently idle ones */ - - /* workers are chained either in the idle_list or busy_hash */ - struct list_head idle_list; /* X: list of idle workers */ - struct hlist_head busy_hash[BUSY_WORKER_HASH_SIZE]; - /* L: hash of busy workers */ - - struct timer_list idle_timer; /* L: worker idle timeout */ - struct timer_list mayday_timer; /* L: SOS timer for dworkers */ - - struct ida worker_ida; /* L: for worker IDs */ - - struct task_struct *trustee; /* L: for gcwq shutdown */ - unsigned int trustee_state; /* L: trustee state */ - wait_queue_head_t trustee_wait; /* trustee wait */ - struct worker *first_idle; /* L: first idle worker */ -} ____cacheline_aligned_in_smp; - -#endif - -struct cpu_workqueue_struct { -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)) - struct worker_pool *pool; /* I: The associated pool */ -#else - struct global_cwq *gcwq; /* I: the associated gcwq */ -#endif - struct workqueue_struct *wq; /* I: the owning workqueue */ - int work_color; /* L: current color */ - int flush_color; /* L: flushing color */ - int nr_in_flight[WORK_NR_COLORS]; - /* L: nr of in_flight works */ - int nr_active; /* L: nr of active works */ - int max_active; /* L: max active works */ - struct list_head delayed_works; /* L: delayed works */ -}; - #endif DECLARE_EVENT_CLASS(workqueue_work, @@ -144,34 +48,33 @@ DECLARE_EVENT_CLASS(workqueue_work, */ TRACE_EVENT(workqueue_queue_work, +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,9,0)) + TP_PROTO(unsigned int req_cpu, struct pool_workqueue *pwq, + struct work_struct *work), + + TP_ARGS(req_cpu, pwq, work), +#else TP_PROTO(unsigned int req_cpu, struct cpu_workqueue_struct *cwq, struct work_struct *work), TP_ARGS(req_cpu, cwq, work), +#endif TP_STRUCT__entry( __field( void *, work ) __field( void *, function) - __field( void *, workqueue) __field( unsigned int, req_cpu ) - __field( unsigned int, cpu ) ), TP_fast_assign( tp_assign(work, work) tp_assign(function, work->func) - tp_assign(workqueue, cwq->wq) tp_assign(req_cpu, req_cpu) -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,6,0)) - tp_assign(cpu, cwq->pool->gcwq->cpu) -#else - tp_assign(cpu, cwq->gcwq->cpu) -#endif ), - TP_printk("work struct=%p function=%pf workqueue=%p req_cpu=%u cpu=%u", - __entry->work, __entry->function, __entry->workqueue, - __entry->req_cpu, __entry->cpu) + TP_printk("work struct=%p function=%pf req_cpu=%u", + __entry->work, __entry->function, + __entry->req_cpu) ) /** diff --git a/probes/lttng-probe-workqueue.c b/probes/lttng-probe-workqueue.c index 6f36e004..f643476f 100644 --- a/probes/lttng-probe-workqueue.c +++ b/probes/lttng-probe-workqueue.c @@ -25,6 +25,7 @@ #include struct cpu_workqueue_struct; +struct pool_workqueue; /* * Create the tracepoint static inlines from the kernel to validate that our