Hi Sebastian,
Sebastian Siewior wrote:
With this patch and
CONFIG_FRAME_POINTER=y
CONFIG_KALLSYMS=y
The backtrace shows resolved function names and their numeric
address.
Signed-off-by: Sebastian Siewior <[EMAIL PROTECTED]>
--- a/arch/m68knommu/kernel/traps.c
+++ b/arch/m68knommu/kernel/traps.c
@@ -28,6 +28,7 @@
#include <linux/linkage.h>
#include <linux/init.h>
#include <linux/ptrace.h>
+#include <linux/kallsyms.h>
#include <asm/setup.h>
#include <asm/fpu.h>
@@ -102,54 +103,47 @@ asmlinkage void buserr_c(struct frame *f
force_sig(SIGSEGV, current);
}
-
int kstack_depth_to_print = 48;
-void show_stack(struct task_struct *task, unsigned long *stack)
+static void __show_stack(struct task_struct *task, unsigned long *stack)
{
unsigned long *endstack, addr;
- extern char _start, _etext;
+ unsigned long *last_stack;
int i;
- if (!stack) {
- if (task)
- stack = (unsigned long *)task->thread.ksp;
- else
- stack = (unsigned long *)&stack;
- }
+ if (!stack)
+ stack = (unsigned long *)task->thread.ksp;
addr = (unsigned long) stack;
endstack = (unsigned long *) PAGE_ALIGN(addr);
printk(KERN_EMERG "Stack from %08lx:", (unsigned long)stack);
for (i = 0; i < kstack_depth_to_print; i++) {
- if (stack + 1 > endstack)
+ if (stack + 1 + i > endstack)
break;
if (i % 8 == 0)
printk("\n" KERN_EMERG " ");
- printk(" %08lx", *stack++);
+ printk(" %08lx", *(stack + i));
}
printk("\n");
- printk(KERN_EMERG "Call Trace:");
- i = 0;
- while (stack + 1 <= endstack) {
- 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) &_start) &&
- (addr <= (unsigned long) &_etext))) {
- if (i % 4 == 0)
- printk("\n" KERN_EMERG " ");
- printk(" [<%08lx>]", addr);
- i++;
- }
+#ifdef CONFIG_FRAME_POINTER
+ printk(KERN_EMERG "Call Trace:\n");
+#else
+ printk(KERN_EMERG "The following call trace is a joke. "
+ "Enable CONFIG_FRAME_POINTER in Kernel Kconfig for usefull "
+ "output.\n");
+#endif
+
+ last_stack = stack - 1;
+ while (stack <= endstack && stack > last_stack) {
+
+ addr = *(stack +1);
+ printk(KERN_EMERG " [%08lx] ", addr);
+ print_symbol(KERN_CONT "%s\n", addr);
+
+ last_stack = stack;
+ stack = (unsigned long *)*stack;
}
printk("\n");
}
I don't like this specific chunk. Seems pointless even trying to
do a symbolic call trace if CONFIG_FRAME_POINTER is disabled.
So I would rather do:
> #ifdef CONFIG_FRAME_POINTER
> printk(KERN_EMERG "Call Trace:\n");
>
> last_stack = stack - 1;
> while (stack <= endstack && stack > last_stack) {
>
> addr = *(stack +1);
> printk(KERN_EMERG " [%08lx] ", addr);
> print_symbol(KERN_CONT "%s\n", addr);
>
> last_stack = stack;
> stack = (unsigned long *)*stack;
154a144,146
> #else
> printk(KERN_EMERG "CONFIG_FRAME_POINTER disabled, no symbolic
call trace\n");
> #endif
Otherwise I am happy with it.
Regards
Greg
@@ -298,19 +292,47 @@ asmlinkage void set_esp0(unsigned long s
current->thread.esp0 = ssp;
}
-
/*
* The architecture-independent backtrace generator
*/
void dump_stack(void)
{
- unsigned long stack;
-
- show_stack(current, &stack);
+ /*
+ * We need frame pointers for this little trick, which works as follows:
+ *
+ * +------------+ 0x00
+ * | Next SP | -> 0x0c
+ * +------------+ 0x04
+ * | Caller |
+ * +------------+ 0x08
+ * | Local vars | -> our stack var
+ * +------------+ 0x0c
+ * | Next SP | -> 0x18, that is what we pass to show_stack()
+ * +------------+ 0x10
+ * | Caller |
+ * +------------+ 0x14
+ * | Local vars |
+ * +------------+ 0x18
+ * | ... |
+ * +------------+
+ */
+
+ unsigned long *stack;
+
+ stack = (unsigned long *)&stack;
+ stack++;
+ __show_stack(current, stack);
}
-
EXPORT_SYMBOL(dump_stack);
+void show_stack(struct task_struct *task, unsigned long *stack)
+{
+ if (!stack && !task)
+ dump_stack();
+ else
+ __show_stack(task, stack);
+}
+
#ifdef CONFIG_M68KFPU_EMU
asmlinkage void fpemu_signal(int signal, int code, void *addr)
{
--
------------------------------------------------------------------------
Greg Ungerer -- Chief Software Dude EMAIL: [EMAIL PROTECTED]
Secure Computing Corporation PHONE: +61 7 3435 2888
825 Stanley St, FAX: +61 7 3891 3630
Woolloongabba, QLD, 4102, Australia WEB: http://www.SnapGear.com
_______________________________________________
uClinux-dev mailing list
uClinux-dev@uclinux.org
http://mailman.uclinux.org/mailman/listinfo/uclinux-dev
This message was resent by uclinux-dev@uclinux.org
To unsubscribe see:
http://mailman.uclinux.org/mailman/options/uclinux-dev