* [PATCH] mini-os: add stack walking debug
@ 2008-07-18 13:02 Samuel Thibault
0 siblings, 0 replies; only message in thread
From: Samuel Thibault @ 2008-07-18 13:02 UTC (permalink / raw)
To: xen-devel
mini-os: add stack walking debug
diff -r 63317b6c3eab extras/mini-os/arch/ia64/sched.c
--- a/extras/mini-os/arch/ia64/sched.c Mon Jul 14 15:21:03 2008 +0100
+++ b/extras/mini-os/arch/ia64/sched.c Fri Jul 18 13:57:44 2008 +0100
@@ -33,6 +33,11 @@
/* The function is implemented in fw.S */
extern void thread_starter(void);
+
+void stack_walk(void)
+{
+ /* TODO */
+}
struct thread*
arch_create_thread(char *name, void (*function)(void *), void *data)
diff -r 63317b6c3eab extras/mini-os/arch/x86/traps.c
--- a/extras/mini-os/arch/x86/traps.c Mon Jul 14 15:21:03 2008 +0100
+++ b/extras/mini-os/arch/x86/traps.c Fri Jul 18 13:57:44 2008 +0100
@@ -112,7 +112,7 @@
printk(" L2 = %"PRIpte" (%p) [offset = %lx]\n", page, tab, l2_table_offset(addr));
page = tab[l1_table_offset(addr)];
- printk(" L1 = %"PRIpte" (%p) [offset = %lx]\n", page, tab, l1_table_offset(addr));
+ printk(" L1 = %"PRIpte" [offset = %lx]\n", page, l1_table_offset(addr));
}
@@ -155,6 +155,40 @@
return 0;
}
+static void do_stack_walk(unsigned long frame_base)
+{
+ unsigned long *frame = (void*) frame_base;
+ printk("base is %#lx ", frame_base);
+ printk("caller is %#lx\n", frame[1]);
+ if (frame[0])
+ do_stack_walk(frame[0]);
+}
+
+void stack_walk(void)
+{
+ unsigned long bp;
+#ifdef __x86_64__
+ asm("movq %%rbp, %0":"=r"(bp));
+#else
+ asm("movl %%ebp, %0":"=r"(bp));
+#endif
+ do_stack_walk(bp);
+}
+
+static void dump_mem(unsigned long addr)
+{
+ unsigned long i;
+ if (addr < PAGE_SIZE)
+ return;
+
+ for (i = ((addr)-16 ) & ~15; i < (((addr)+48 ) & ~15); i++)
+ {
+ if (!(i%16))
+ printk("\n%lx:", i);
+ printk(" %02x", *(unsigned char *)i);
+ }
+ printk("\n");
+}
#define read_cr2() \
(HYPERVISOR_shared_info->vcpu_info[smp_processor_id()].arch.cr2)
@@ -163,6 +197,7 @@
void do_page_fault(struct pt_regs *regs, unsigned long error_code)
{
unsigned long addr = read_cr2();
+ struct sched_shutdown sched_shutdown = { .reason = SHUTDOWN_crash };
if ((error_code & TRAP_PF_WRITE) && handle_cow(addr))
return;
@@ -170,37 +205,61 @@
/* If we are already handling a page fault, and got another one
that means we faulted in pagetable walk. Continuing here would cause
a recursive fault */
- if(handling_pg_fault)
+ if(handling_pg_fault == 1)
{
printk("Page fault in pagetable walk (access to invalid memory?).\n");
- do_exit();
+ HYPERVISOR_sched_op(SCHEDOP_shutdown, &sched_shutdown);
}
- handling_pg_fault = 1;
+ handling_pg_fault++;
+ barrier();
#if defined(__x86_64__)
- printk("Page fault at linear address %p, rip %p, code %lx\n",
- addr, regs->rip, error_code);
+ printk("Page fault at linear address %p, rip %p, regs %p, sp %p, our_sp %p, code %lx\n",
+ addr, regs->rip, regs, regs->rsp, &addr, error_code);
#else
- printk("Page fault at linear address %p, eip %p, code %lx\n",
- addr, regs->eip, error_code);
+ printk("Page fault at linear address %p, eip %p, regs %p, sp %p, our_sp %p, code %lx\n",
+ addr, regs->eip, regs, regs->esp, &addr, error_code);
#endif
dump_regs(regs);
+#if defined(__x86_64__)
+ do_stack_walk(regs->rbp);
+ dump_mem(regs->rsp);
+ dump_mem(regs->rbp);
+ dump_mem(regs->rip);
+#else
+ do_stack_walk(regs->ebp);
+ dump_mem(regs->esp);
+ dump_mem(regs->ebp);
+ dump_mem(regs->eip);
+#endif
page_walk(addr);
- do_exit();
+ HYPERVISOR_sched_op(SCHEDOP_shutdown, &sched_shutdown);
/* We should never get here ... but still */
- handling_pg_fault = 0;
+ handling_pg_fault--;
}
void do_general_protection(struct pt_regs *regs, long error_code)
{
+ struct sched_shutdown sched_shutdown = { .reason = SHUTDOWN_crash };
#ifdef __i386__
printk("GPF eip: %p, error_code=%lx\n", regs->eip, error_code);
#else
printk("GPF rip: %p, error_code=%lx\n", regs->rip, error_code);
#endif
dump_regs(regs);
- do_exit();
+#if defined(__x86_64__)
+ do_stack_walk(regs->rbp);
+ dump_mem(regs->rsp);
+ dump_mem(regs->rbp);
+ dump_mem(regs->rip);
+#else
+ do_stack_walk(regs->ebp);
+ dump_mem(regs->esp);
+ dump_mem(regs->ebp);
+ dump_mem(regs->eip);
+#endif
+ HYPERVISOR_sched_op(SCHEDOP_shutdown, &sched_shutdown);
}
diff -r 63317b6c3eab extras/mini-os/include/ia64/traps.h
--- a/extras/mini-os/include/ia64/traps.h Mon Jul 14 15:21:03 2008 +0100
+++ b/extras/mini-os/include/ia64/traps.h Fri Jul 18 13:57:44 2008 +0100
@@ -48,5 +48,7 @@
#include "ia64_cpu.h"
+void stack_walk(void);
+
#endif /* !defined(_TRAPS_H_) */
diff -r 63317b6c3eab extras/mini-os/include/x86/traps.h
--- a/extras/mini-os/include/x86/traps.h Mon Jul 14 15:21:03 2008 +0100
+++ b/extras/mini-os/include/x86/traps.h Fri Jul 18 13:57:44 2008 +0100
@@ -69,6 +69,7 @@
#endif
void dump_regs(struct pt_regs *regs);
+void stack_walk(void);
#define TRAP_PF_PROT 0x1
#define TRAP_PF_WRITE 0x2
diff -r 63317b6c3eab extras/mini-os/kernel.c
--- a/extras/mini-os/kernel.c Mon Jul 14 15:21:03 2008 +0100
+++ b/extras/mini-os/kernel.c Fri Jul 18 13:57:44 2008 +0100
@@ -592,6 +592,7 @@
void do_exit(void)
{
printk("Do_exit called!\n");
+ stack_walk();
for( ;; )
{
struct sched_shutdown sched_shutdown = { .reason = SHUTDOWN_crash };
^ permalink raw reply [flat|nested] only message in thread
only message in thread, other threads:[~2008-07-18 13:02 UTC | newest]
Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-07-18 13:02 [PATCH] mini-os: add stack walking debug Samuel Thibault
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.