From 600dd0bb30d9d8d5c7645156c1c50ad68ec1b334 Mon Sep 17 00:00:00 2001
From: dzwdz
Date: Tue, 3 May 2022 19:02:56 +0200
Subject: kernel: stacktraces on panic()

---
 src/kernel/arch/generic.h    |  6 +++++-
 src/kernel/arch/i386/debug.c | 18 ++++++++++++++++++
 src/kernel/panic.h           |  5 +++--
 3 files changed, 26 insertions(+), 3 deletions(-)
 create mode 100644 src/kernel/arch/i386/debug.c

(limited to 'src/kernel')

diff --git a/src/kernel/arch/generic.h b/src/kernel/arch/generic.h
index f8dfe51..fd44e38 100644
--- a/src/kernel/arch/generic.h
+++ b/src/kernel/arch/generic.h
@@ -2,8 +2,9 @@
 
 #include <kernel/arch/i386/registers.h>
 #include <shared/types.h>
-#include <stdbool.h>
 #include <stdarg.h>
+#include <stdbool.h>
+#include <stddef.h>
 
 // i have no idea where else to put it
 // some code assumes that it's a power of 2
@@ -39,3 +40,6 @@ void *pagedir_virt2phys(struct pagedir *dir, const void __user *virt,
                         bool user, bool writeable);
 
 int kprintf(const char *fmt, ...);
+
+void *debug_caller(size_t depth);
+void debug_stacktrace(void);
diff --git a/src/kernel/arch/i386/debug.c b/src/kernel/arch/i386/debug.c
new file mode 100644
index 0000000..b1920db
--- /dev/null
+++ b/src/kernel/arch/i386/debug.c
@@ -0,0 +1,18 @@
+#include <kernel/arch/generic.h>
+
+void *debug_caller(size_t depth) {
+	void **ebp;
+	asm("mov %%ebp, %0" 
+	    : "=r" (ebp));
+	while (depth--) {
+		if (!ebp) return NULL;
+		ebp = *ebp;
+	}
+	return ebp[1];
+}
+
+void debug_stacktrace(void) {
+	for (size_t i = 0; i < 16; i++) {
+		kprintf("  k/%08x\n", (uintptr_t)debug_caller(i));
+	}
+}
diff --git a/src/kernel/panic.h b/src/kernel/panic.h
index c4cd194..8cb32f4 100644
--- a/src/kernel/panic.h
+++ b/src/kernel/panic.h
@@ -3,9 +3,10 @@
 #include <kernel/util.h>
 
 #define _panic(type) do { \
-	kprintf(" an "type" PANIC! at the "); \
+	kprintf("\nan "type" PANIC! at the "); \
 	kprintf(__func__); \
-	kprintf(" (" __FILE__ ":" NUM2STR(__LINE__) ") "); \
+	kprintf(" (" __FILE__ ":" NUM2STR(__LINE__) ")\n"); \
+	debug_stacktrace(); \
 	halt_cpu(); \
 } while (0)
 
-- 
cgit v1.2.3