[Crash-utility] [PATCH] Make bt -a accept a CPU as an argument

Aaron Tomlin atomlin at redhat.com
Sat Apr 26 15:06:32 UTC 2014


Currently 'bt -a' displays the stack traces of the active task on each
CPU. This patch makes it possible to specify a CPU as an argument.
Multiple CPU arguments may be specified. If no argument is given
the default behaviour is maintained.

For example:

Display the stack trace of the active task on CPU 0 and 1:

  crash> bt -a 0 1
  PID: 0      TASK: ffffffff81a8d020  CPU: 0   COMMAND: "swapper"
   #0 [ffff880002207e90] crash_nmi_callback at ffffffff8102fee6
   #1 [ffff880002207ea0] notifier_call_chain at ffffffff8152d525
   #2 [ffff880002207ee0] atomic_notifier_call_chain at ffffffff8152d58a
   #3 [ffff880002207ef0] notify_die at ffffffff810a155e
   #4 [ffff880002207f20] do_nmi at ffffffff8152b1eb
   #5 [ffff880002207f50] nmi at ffffffff8152aab0
      [exception RIP: native_safe_halt+0xb]
      RIP: ffffffff8103eacb  RSP: ffffffff81a01ea8  RFLAGS: 00000296
      RAX: 0000000000000000  RBX: 0000000000000000  RCX: 0000000000000000
      RDX: 0000000000000000  RSI: 0000000000000001  RDI: ffffffff81de5228
      RBP: ffffffff81a01ea8   R8: 0000000000000000   R9: 0000000000000000
      R10: 0012099429a6bea3  R11: 0000000000000000  R12: ffffffff81c066c0
      R13: 0000000000000000  R14: ffffffffffffffff  R15: ffffffff81de1000
      ORIG_RAX: ffffffffffffffff  CS: 0010  SS: 0018
  --- <NMI exception stack> ---
   #6 [ffffffff81a01ea8] native_safe_halt at ffffffff8103eacb
   #7 [ffffffff81a01eb0] default_idle at ffffffff810167bd
   #8 [ffffffff81a01ed0] cpu_idle at ffffffff81009fc6

  PID: 38     TASK: ffff88003eaae040  CPU: 1   COMMAND: "khungtaskd"
   #0 [ffff88003ad97ce8] machine_kexec at ffffffff81038f3b
   #1 [ffff88003ad97d48] crash_kexec at ffffffff810c5da2
   #2 [ffff88003ad97e18] panic at ffffffff8152721a
   #3 [ffff88003ad97e98] watchdog at ffffffff810e6346
   #4 [ffff88003ad97ee8] kthread at ffffffff8109af06
   #5 [ffff88003ad97f48] kernel_thread at ffffffff8100c20a

Signed-off-by: Aaron Tomlin <atomlin at redhat.com>
---
 help.c   | 37 ++++++++++++++++++++++++++++++++++---
 kernel.c | 26 +++++++++++++++++++++++---
 2 files changed, 57 insertions(+), 6 deletions(-)

diff --git a/help.c b/help.c
index 91f22c3..62af23a 100644
--- a/help.c
+++ b/help.c
@@ -1704,11 +1704,13 @@ NULL
 char *help_bt[] = {
 "bt",
 "backtrace",
-"[-a|-g|-r|-t|-T|-l|-e|-E|-f|-F|-o|-O] [-R ref] [-s [-x|d]] [-I ip] [-S sp]"
+"[-a [cpu]|-g|-r|-t|-T|-l|-e|-E|-f|-F|-o|-O] [-R ref] [-s [-x|d]] [-I ip] [-S sp]"
 "\n     [pid | task]",
 "  Display a kernel stack backtrace.  If no arguments are given, the stack",
 "  trace of the current context will be displayed.\n",
-"       -a  displays the stack traces of the active task on each CPU.",
+"       -a  display the stack trace of the active task on a given CPU.",
+"           Multiple CPU arguments may be specified. If no arguments are given",
+"           the stack trace of the active task on each CPU is shown.",
 "           (only applicable to crash dumps)",
 #ifdef GDB_5_3
 "       -g  use gdb stack trace code. (alpha only)",
@@ -1766,7 +1768,36 @@ char *help_bt[] = {
 "  or display a stale frame reference.  When in doubt as to the accuracy of a",
 "  backtrace, the -t or -T options may help fill in the blanks.\n",
 "EXAMPLES",
-"  Display the stack trace of the active task(s) when the kernel panicked:\n",
+"  Display the stack trace of the active task on CPU 0 and 1:\n",
+"    %s> bt -a 0 1",
+"    PID: 0      TASK: ffffffff81a8d020  CPU: 0   COMMAND: \"swapper\"",
+"     #0 [ffff880002207e90] crash_nmi_callback at ffffffff8102fee6",
+"     #1 [ffff880002207ea0] notifier_call_chain at ffffffff8152d525",
+"     #2 [ffff880002207ee0] atomic_notifier_call_chain at ffffffff8152d58a",
+"     #3 [ffff880002207ef0] notify_die at ffffffff810a155e",
+"     #4 [ffff880002207f20] do_nmi at ffffffff8152b1eb",
+"     #5 [ffff880002207f50] nmi at ffffffff8152aab0",
+"        [exception RIP: native_safe_halt+0xb]",
+"        RIP: ffffffff8103eacb  RSP: ffffffff81a01ea8  RFLAGS: 00000296",
+"        RAX: 0000000000000000  RBX: 0000000000000000  RCX: 0000000000000000",
+"        RDX: 0000000000000000  RSI: 0000000000000001  RDI: ffffffff81de5228",
+"        RBP: ffffffff81a01ea8   R8: 0000000000000000   R9: 0000000000000000",
+"        R10: 0012099429a6bea3  R11: 0000000000000000  R12: ffffffff81c066c0",
+"        R13: 0000000000000000  R14: ffffffffffffffff  R15: ffffffff81de1000",
+"        ORIG_RAX: ffffffffffffffff  CS: 0010  SS: 0018",
+"    --- <NMI exception stack> ---",
+"     #6 [ffffffff81a01ea8] native_safe_halt at ffffffff8103eacb",
+"     #7 [ffffffff81a01eb0] default_idle at ffffffff810167bd",
+"     #8 [ffffffff81a01ed0] cpu_idle at ffffffff81009fc6",
+" ",
+"    PID: 38     TASK: ffff88003eaae040  CPU: 1   COMMAND: \"khungtaskd\"",
+"     #0 [ffff88003ad97ce8] machine_kexec at ffffffff81038f3b",
+"     #1 [ffff88003ad97d48] crash_kexec at ffffffff810c5da2",
+"     #2 [ffff88003ad97e18] panic at ffffffff8152721a",
+"     #3 [ffff88003ad97e98] watchdog at ffffffff810e6346",
+"     #4 [ffff88003ad97ee8] kthread at ffffffff8109af06",
+"     #5 [ffff88003ad97f48] kernel_thread at ffffffff8100c20a",
+"\n  Display the stack trace of the active task(s) when the kernel panicked:\n",
 "    %s> bt -a",
 "    PID: 286    TASK: c0b3a000  CPU: 0   COMMAND: \"in.rlogind\"",
 "    #0 [c0b3be90] crash_save_current_state at c011aed0",
diff --git a/kernel.c b/kernel.c
index cdc53eb..6b3e25b 100644
--- a/kernel.c
+++ b/kernel.c
@@ -1972,15 +1972,15 @@ cmd_bt(void)
 	int i, c;
 	ulong value;
         struct task_context *tc;
-	int count, subsequent, active;
+	int count, subsequent, active, cpu;
 	struct stack_hook hook;
 	struct bt_info bt_info, bt_setup, *bt;
 	struct reference reference;
 	char *refptr;
-	ulong tgid;
+	ulong tgid, task;
 
 	tc = NULL;
-	subsequent = active = count = 0;
+	subsequent = active = count = cpu = 0;
 	hook.eip = hook.esp = 0;
 	refptr = 0;
 	bt = &bt_info;
@@ -2232,6 +2232,26 @@ cmd_bt(void)
 			error(FATAL, 
 			    "-a option cannot be used with the -g option\n");
 
+		while (args[optind]) {
+			cpu = dtoi(args[optind], FAULT_ON_ERROR, NULL);
+			if (cpu >= kt->cpus) {
+				error(FATAL, "invalid cpu number: system has only %d cpu%s\n",
+					kt->cpus, kt->cpus > 1 ? "s" : "");
+				return;
+			}
+			if ((task = get_active_task(cpu)))
+				tc = task_to_context(task);
+			else  {
+				error(FATAL, "cannot determine active task on cpu %ld\n", cpu);
+				return;
+			}
+			DO_TASK_BACKTRACE();
+
+			optind++;
+			if (!args[optind])
+				return;
+		}
+
 		for (c = 0; c < NR_CPUS; c++) {
 			if (setjmp(pc->foreach_loop_env)) {
 				pc->flags &= ~IN_FOREACH;
-- 
1.9.0




More information about the Crash-utility mailing list