X-Git-Url: http://git.onelab.eu/?a=blobdiff_plain;ds=sidebyside;f=arch%2Fparisc%2Fkernel%2Ftraps.c;h=ff80b3c1f8a2765ea51b7f440dfaf5032e919b23;hb=9bf4aaab3e101692164d49b7ca357651eb691cb6;hp=6f1f6f738d6c037722f73ebb8ffa454d6d8c3d82;hpb=db216c3d5e4c040e557a50f8f5d35d5c415e8c1c;p=linux-2.6.git diff --git a/arch/parisc/kernel/traps.c b/arch/parisc/kernel/traps.c index 6f1f6f738..ff80b3c1f 100644 --- a/arch/parisc/kernel/traps.c +++ b/arch/parisc/kernel/traps.c @@ -38,12 +38,17 @@ #include #include #include +#include #include "../math-emu/math-emu.h" /* for handle_fpe() */ #define PRINT_USER_FAULTS /* (turn this on if you want user faults to be */ /* dumped to the console via printk) */ +#if defined(CONFIG_SMP) || defined(CONFIG_DEBUG_SPINLOCK) +spinlock_t pa_dbit_lock = SPIN_LOCK_UNLOCKED; +#endif + int printbinary(char *buf, unsigned long x, int nbits) { unsigned long mask = 1UL << (nbits - 1); @@ -125,73 +130,37 @@ void show_regs(struct pt_regs *regs) void dump_stack(void) { - unsigned long stack; - show_trace(current, &stack); + show_stack(NULL, NULL); } EXPORT_SYMBOL(dump_stack); -#ifndef __LP64__ -static int kstack_depth_to_print = 64 * 4; -#else -static int kstack_depth_to_print = 128 * 4; -#endif - -void show_stack(struct task_struct *task, unsigned long *sp) +void show_stack(struct task_struct *task, unsigned long *s) { - unsigned long *stack; - int i; - - /* - * debugging aid: "show_stack(NULL);" prints the - * back trace for this cpu. - */ - if (task==NULL) - sp = (unsigned long*)&sp; - else if(sp == NULL) - sp = (unsigned long*)task->thread.regs.ksp; - - stack = sp; - printk("\n" KERN_CRIT "Stack Dump:\n"); - printk(KERN_CRIT " " RFMT ": ", (unsigned long) stack); - for (i=0; i < kstack_depth_to_print; i++) { - if (((long) stack & (THREAD_SIZE-1)) == 0) - break; - if (i && ((i & 0x03) == 0)) - printk("\n" KERN_CRIT " " RFMT ": ", - (unsigned long) stack); - printk(RFMT " ", *stack--); + int i = 1; + struct unwind_frame_info info; + + if (!task) { + unsigned long sp, ip, rp; + +HERE: + asm volatile ("copy %%r30, %0" : "=r"(sp)); + ip = (unsigned long)&&HERE; + rp = (unsigned long)__builtin_return_address(0); + unwind_frame_init(&info, current, sp, ip, rp); + } else { + unwind_frame_init_from_blocked_task(&info, task); } - printk("\n" KERN_CRIT "\n"); - show_trace(task, sp); -} + printk("Backtrace:\n"); + while (i <= 16) { + if (unwind_once(&info) < 0 || info.ip == 0) + break; -void show_trace(struct task_struct *task, unsigned long *stack) -{ - unsigned long *startstack; - unsigned long addr; - int i; - - startstack = (unsigned long *)((unsigned long)stack & ~(THREAD_SIZE - 1)); - i = 1; - stack = (long *)((long)(stack + 32) &~ (FRAME_SIZE-1)); /* Align */ - printk("Kernel addresses on the stack:\n"); - while (stack > startstack) { - stack -= 16; /* Stack frames are a multiple of 16 words */ - addr = stack[16 - RP_OFFSET / sizeof(long)]; - /* - * 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 (kernel_text_address(addr)) { - printk(" [<" RFMT ">] ", addr); + if (__kernel_text_address(info.ip)) { + printk(" [<" RFMT ">] ", info.ip); #ifdef CONFIG_KALLSYMS - print_symbol("%s\n", addr); + print_symbol("%s\n", info.ip); #else if ((i & 0x03) == 0) printk("\n");