The problem with small dmesg ring buffer like 512k is that only limited number of task traces will be logged. Sometimes we lose important information only because of too many duplicated stack traces. This problem occurs when dumping lots of stacks in a single operation, such as sysrq-T. This patch tries to reduce the duplication of task stack trace in the dump message by hashing the task stack. The hashtable is a 32k pre-allocated buffer during bootup. Each time if we find the identical task trace in the task stack, we dump only the pid of the task which has the task trace dumped. So it is easy to back track to the full stack with the pid. When we do the hashing, we eliminate garbage entries from stack traces. Those entries are still being printed in the dump to provide more debugging informations. [ 53.510162] kworker/0:0 S ffffffff8161d820 0 4 2 0x00000000 [ 53.517237] ffff88027547de60 0000000000000046 ffffffff812ab840 0000000000000000 [ 53.524663] ffff880275460080 ffff88027547dfd8 ffff88027547dfd8 ffff88027547dfd8 [ 53.532092] ffffffff81813020 ffff880275460080 0000000000000000 ffff8808758670c0 [ 53.539521] Call Trace: [ 53.541974] [<ffffffff812ab840>] ? cfq_init_queue+0x350/0x350 [ 53.547791] [<ffffffff81524d49>] schedule+0x29/0x70 [ 53.552761] [<ffffffff810945a3>] worker_thread+0x233/0x380 [ 53.558318] [<ffffffff81094370>] ? manage_workers.isra.28+0x230/0x230 [ 53.564839] [<ffffffff81099a73>] kthread+0x93/0xa0 [ 53.569714] [<ffffffff8152e6d4>] kernel_thread_helper+0x4/0x10 [ 53.575628] [<ffffffff810999e0>] ? kthread_worker_fn+0x140/0x140 [ 53.581714] [<ffffffff8152e6d0>] ? gs_change+0xb/0xb [ 53.586762] kworker/u:0 S ffffffff8161d820 0 5 2 0x00000000 [ 53.593858] ffff88027547fe60 0000000000000046 ffffffffa005cc70 0000000000000000 [ 53.601307] ffff8802754627d0 ffff88027547ffd8 ffff88027547ffd8 ffff88027547ffd8 [ 53.608788] ffffffff81813020 ffff8802754627d0 0000000000011fc0 ffff8804758670c0 [ 53.616232] Call Trace: [ 53.618676] <Same stack as pid 4> Signed-off-by: Ying Han <yinghan@google.com> Acked-by: Rik van Riel <riel@redhat.com> [abrestic: rebased on 3.8, fixed build for ARM] Signed-off-by: Andrew Bresticker <abrestic@chromium.org> Patch posted upstream at: https://lkml.org/lkml/2012/4/6/238 BUG=chromium:294982 TEST=On lumpy, dump tasks and observe that 209 of 258 task dumps have been de-duplicated: localhost ~ # echo t > /proc/sysrq-trigger localhost ~ # grep "Call Trace:" /var/log/messages | wc -l 258 localhost ~ # grep "Same stack as" /var/log/messages | wc -l 209 Change-Id: I81de919dc2f1006127c4e1c0bfee13d4f822b5b1 Reviewed-on: https://chromium-review.googlesource.com/169957 Reviewed-by: Sameer Nanda <snanda@chromium.org> Commit-Queue: Andrew Bresticker <abrestic@chromium.org> Tested-by: Andrew Bresticker <abrestic@chromium.org>
42 lines
1.2 KiB
C
42 lines
1.2 KiB
C
#ifndef __LINUX_STACKTRACE_H
|
|
#define __LINUX_STACKTRACE_H
|
|
|
|
struct task_struct;
|
|
struct pt_regs;
|
|
|
|
#ifdef CONFIG_STACKTRACE
|
|
struct task_struct;
|
|
|
|
struct stack_trace {
|
|
unsigned int nr_entries, max_entries;
|
|
unsigned long *entries;
|
|
int skip; /* input argument: How many entries to skip */
|
|
};
|
|
|
|
extern void save_stack_trace(struct stack_trace *trace);
|
|
extern void save_stack_trace_regs(struct pt_regs *regs,
|
|
struct stack_trace *trace);
|
|
extern void save_stack_trace_tsk(struct task_struct *tsk,
|
|
struct stack_trace *trace);
|
|
|
|
extern void print_stack_trace(struct stack_trace *trace, int spaces);
|
|
|
|
extern void clear_dup_stack_traces(void);
|
|
extern unsigned int save_dup_stack_trace(struct task_struct *tsk);
|
|
#ifdef CONFIG_USER_STACKTRACE_SUPPORT
|
|
extern void save_stack_trace_user(struct stack_trace *trace);
|
|
#else
|
|
# define save_stack_trace_user(trace) do { } while (0)
|
|
#endif
|
|
|
|
#else
|
|
# define save_stack_trace(trace) do { } while (0)
|
|
# define save_stack_trace_tsk(tsk, trace) do { } while (0)
|
|
# define save_stack_trace_user(trace) do { } while (0)
|
|
# define print_stack_trace(trace, spaces) do { } while (0)
|
|
# define clear_dup_stack_traces() do { } while (0)
|
|
# define save_dup_stack_trace(tsk) do { } while (0)
|
|
#endif
|
|
|
|
#endif
|