--Matt
On Sun, 21 Nov 1999, Keith Owens wrote:
|>On Sat, 20 Nov 1999 14:38:40 +0100 (CET),
|>Ingo Molnar <mingo@chiara.csoma.elte.hu> wrote:
|>>On Thu, 18 Nov 1999, Dominik Kubla wrote:
|>>> Hmm... nice! Is there a way to get a stacktrace without forcing an oops?
|>>nevertheless just changing show_task() or die_if_kernel() to not crash the
|>>the process if called in some special way could indeed be a welcome
|>>addition - but i believe only if it doesnt increase maintainance efforts.
|>
|>Easier than that. Break the stack dump code from show_registers() into
|>a separate routine, patch below. Any code that needs a back trace for
|>debugging can call show_stack(NULL). This also fixes a long standing
|>bug where the i386 stack was not completely printed if it went into the
|>second stack page.
|>
|>This patch is only for i386. It would be nice if all architectures had
|>a standard show_stack() routine. Against 2.3.28.
|>
|>Index: 28.1/arch/i386/kernel/i386_ksyms.c
|>--- 28.1/arch/i386/kernel/i386_ksyms.c Fri, 12 Nov 1999 18:53:00 +1100 keith (linux-2.3/w/37_i386_ksyms 1.9 644)
|>+++ 28.1(w)/arch/i386/kernel/i386_ksyms.c Sun, 21 Nov 1999 13:33:31 +1100 keith (linux-2.3/w/37_i386_ksyms 1.9 644)
|>@@ -130,3 +130,4 @@
|> #endif
|>
|> EXPORT_SYMBOL(get_wchan);
|>+EXPORT_SYMBOL(show_stack); /* For adhoc debugging in modules */
|>Index: 28.1/arch/i386/kernel/traps.c
|>--- 28.1/arch/i386/kernel/traps.c Sat, 23 Oct 1999 15:35:04 +1000 keith (linux-2.3/x/0_traps.c 1.7 644)
|>+++ 28.1(w)/arch/i386/kernel/traps.c Sun, 21 Nov 1999 19:58:17 +1100 keith (linux-2.3/x/0_traps.c 1.7 644)
|>@@ -129,13 +129,59 @@
|> #define VMALLOC_OFFSET (8*1024*1024)
|> #define MODULE_RANGE (8*1024*1024)
|>
|>+/* Separate show_stack() so adhoc debugging code can use it */
|>+void show_stack(const unsigned long *esp)
|>+{
|>+ int i;
|>+ unsigned long *stack, *save_stack, addr, module_start, module_end;
|>+ printk("Stack: ");
|>+ /* show_registers passes a real esp, adhoc debugging passes NULL */
|>+ if (esp)
|>+ stack = (unsigned long *) esp;
|>+ else
|>+ asm("movl %%esp,%0": "=m" (stack));
|>+ save_stack = stack;
|>+ for(i=0; i < kstack_depth_to_print; i++) {
|>+ if (((long) stack & ~PAGE_MASK) == 0)
|>+ break;
|>+ if (i && ((i % 8) == 0))
|>+ printk("\n ");
|>+ printk("%08lx ", *stack++);
|>+ }
|>+ printk("\nCall Trace: ");
|>+ stack = save_stack;
|>+ i = 1;
|>+ module_start = PAGE_OFFSET + (max_mapnr << PAGE_SHIFT);
|>+ module_start = ((module_start + VMALLOC_OFFSET) & ~(VMALLOC_OFFSET-1));
|>+ module_end = module_start + MODULE_RANGE;
|>+ while (((long) stack & ~PAGE_MASK) != 0) {
|>+ addr = *stack++;
|>+ /*
|>+ * If the address is either in the text segment of the
|>+ * kernel, or in the region which contains vmalloc'ed
|>+ * memory, it *may* be the address of a calling
|>+ * routine; if so, print it so that someone tracing
|>+ * down the cause of the crash will be able to figure
|>+ * out the call path that was taken.
|>+ */
|>+ if (((addr >= (unsigned long) &_stext) &&
|>+ (addr <= (unsigned long) &_etext)) ||
|>+ ((addr >= module_start) && (addr <= module_end))) {
|>+ if (i && ((i % 8) == 0))
|>+ printk("\n ");
|>+ printk("[<%08lx>] ", addr);
|>+ i++;
|>+ }
|>+ }
|>+ printk("\n");
|>+}
|>+
|> static void show_registers(struct pt_regs *regs)
|> {
|> int i;
|> int in_kernel = 1;
|> unsigned long esp;
|> unsigned short ss;
|>- unsigned long *stack, addr, module_start, module_end;
|>
|> esp = (unsigned long) (1+regs);
|> ss = __KERNEL_DS;
|>@@ -152,52 +198,19 @@
|> regs->esi, regs->edi, regs->ebp, esp);
|> printk("ds: %04x es: %04x ss: %04x\n",
|> regs->xds & 0xffff, regs->xes & 0xffff, ss);
|>- printk("Process %s (pid: %d, stackpage=%08lx)",
|>+ printk("Process %s (pid: %d, stackpage=%08lx)\n",
|> current->comm, current->pid, 4096+(unsigned long)current);
|> /*
|> * When in-kernel, we also print out the stack and code at the
|> * time of the fault..
|> */
|> if (in_kernel) {
|>- printk("\nStack: ");
|>- stack = (unsigned long *) esp;
|>- for(i=0; i < kstack_depth_to_print; i++) {
|>- if (((long) stack & 4095) == 0)
|>- break;
|>- if (i && ((i % 8) == 0))
|>- printk("\n ");
|>- printk("%08lx ", *stack++);
|>- }
|>- printk("\nCall Trace: ");
|>- stack = (unsigned long *) esp;
|>- i = 1;
|>- module_start = PAGE_OFFSET + (max_mapnr << PAGE_SHIFT);
|>- module_start = ((module_start + VMALLOC_OFFSET) & ~(VMALLOC_OFFSET-1));
|>- module_end = module_start + MODULE_RANGE;
|>- while (((long) stack & 4095) != 0) {
|>- addr = *stack++;
|>- /*
|>- * If the address is either in the text segment of the
|>- * kernel, or in the region which contains vmalloc'ed
|>- * memory, it *may* be the address of a calling
|>- * routine; if so, print it so that someone tracing
|>- * down the cause of the crash will be able to figure
|>- * out the call path that was taken.
|>- */
|>- if (((addr >= (unsigned long) &_stext) &&
|>- (addr <= (unsigned long) &_etext)) ||
|>- ((addr >= module_start) && (addr <= module_end))) {
|>- if (i && ((i % 8) == 0))
|>- printk("\n ");
|>- printk("[<%08lx>] ", addr);
|>- i++;
|>- }
|>- }
|>- printk("\nCode: ");
|>+ show_stack(&esp);
|>+ printk("Code: ");
|> for(i=0;i<20;i++)
|> printk("%02x ", ((unsigned char *)regs->eip)[i]);
|>+ printk("\n");
|> }
|>- printk("\n");
|> }
|>
|> spinlock_t die_lock;
|>Index: 28.1/include/linux/kernel.h
|>--- 28.1/include/linux/kernel.h Sat, 23 Oct 1999 15:35:04 +1000 keith (linux-2.3/F/b/4_kernel.h 1.7 644)
|>+++ 28.1(w)/include/linux/kernel.h Sun, 21 Nov 1999 14:08:36 +1100 keith (linux-2.3/F/b/4_kernel.h 1.7 644)
|>@@ -42,6 +42,7 @@
|> #define FASTCALL(x) x
|> #endif
|>
|>+extern void show_stack(const unsigned long *); /* For adhoc debugging */
|> extern void math_error(void);
|> extern struct notifier_block *panic_notifier_list;
|> NORET_TYPE void panic(const char * fmt, ...)
|>
|>
|>-
|>To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
|>the body of a message to majordomo@vger.rutgers.edu
|>Please read the FAQ at http://www.tux.org/lkml/
|>
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/