diff options
Diffstat (limited to 'stage3')
-rw-r--r-- | stage3/debug.c | 97 | ||||
-rw-r--r-- | stage3/init.c | 3 | ||||
-rw-r--r-- | stage3/isr.lua | 13 | ||||
-rw-r--r-- | stage3/main.c | 6 | ||||
-rw-r--r-- | stage3/paging.asm | 15 | ||||
-rw-r--r-- | stage3/watchdog.lua | 4 |
6 files changed, 87 insertions, 51 deletions
diff --git a/stage3/debug.c b/stage3/debug.c index 0621dbd..ed28fee 100644 --- a/stage3/debug.c +++ b/stage3/debug.c @@ -4,7 +4,6 @@ #include "halt.h" #include "debug.h" -static str dbg_map = NILS; static str dbg_disas = NILS; static str exception[32] = { @@ -37,56 +36,70 @@ static str exception[32] = { NILS, }; -static void dump_frame(interrupt_frame *frame) +static bool get_source(u64 code, str *func, str *linep) { - print(S("rip = ")); - print_hex(frame->rip); - - if (dbg_map.data != nil) { - str entry = NILS; - str iter = dbg_map; - while (iter.len > 0) { - str line = str_walk(&iter, S("\n")); - line = str_eat(line, S(" ")); - if (!str_start(line, S("0x"))) + if (dbg_disas.data == nil) + return false; + + *func = (str) NILS; + *linep = (str) NILS; + + str iter = dbg_disas; + while (iter.len > 0) { + str line = str_walk(&iter, S("\n")); + u64 func_addr; + usize adv; + if ((adv = str_parse_num(line, 16, &func_addr))) { + line = str_advance(line, adv); + if (line.len < 2 || line.data[0] != ' ' || line.data[1] != '<') continue; line = str_advance(line, 2); - + usize close = str_find(line, S(">")); + *func = (str) { .len = close, .data = line.data }; + } else { u64 addr; - usize adv = str_parse_num(line, 16, &addr); - if (adv == 0) + if (!str_parse_num(str_eat(line, S(" ")), 16, &addr)) continue; - line = str_advance(line, adv); - - if (addr > frame->rip) - break; - - line = str_eat(line, S(" ")); - if (line.len > 0) - entry = line; + *linep = line; + if (addr == code) + return true; } + } - if (entry.len > 0) { - print(S(" in ")); - print(entry); - } + return false; +} + +static void trace(u64 code, u64 base) +{ + if (base == 0) + return; + + str func, line; + if (get_source(code, &func, &line)) { + print(S("\t")); + print_hex(code); + print(S(" in ")); + print(func); + print(S("\n")); } - if (dbg_disas.data != nil) { - str iter = dbg_disas; - while (iter.len > 0) { - str line = str_walk(&iter, S("\n")); - u64 addr; - if (!str_parse_num(str_eat(line, S(" ")), 16, &addr)) - continue; - if (addr == frame->rip) { - print(S("\n")); - print(line); - break; - } - } + u64 *stack = (u64 *) base; + trace(stack[1], stack[0]); +} + +static void dump_frame(interrupt_frame *frame) +{ + str func, line; + if (get_source(frame->rip, &func, &line)) { + print(line); + print(S("\n")); } + print(S("backtrace:\n")); + trace(frame->rip, frame->rbp); + + print(S("rip = ")); + print_hex(frame->rip); print(S("\n")); struct { @@ -187,7 +200,7 @@ void debug_exception(interrupt_frame *frame) void debug_init() { - print(S("loading kernel debug info...\n")); - dbg_map = fs_read(S("dbg/kernel.map")); + print(S("loading kernel debug info... ")); dbg_disas = fs_read(S("dbg/kernel.dis.asm")); + print(S("done\n")); } diff --git a/stage3/init.c b/stage3/init.c index 2e26e19..c65f08b 100644 --- a/stage3/init.c +++ b/stage3/init.c @@ -1,7 +1,7 @@ #include "def.h" void kmain(); -void init() +void _start() { // enable SSE. long mode demands it is present u64 cr0; @@ -14,5 +14,6 @@ void init() u16 fpu_cw = 0x37a; asm volatile("fldcw %0"::"m"(fpu_cw)); + kmain(); } diff --git a/stage3/isr.lua b/stage3/isr.lua index 3c88c5e..4810f01 100644 --- a/stage3/isr.lua +++ b/stage3/isr.lua @@ -6,6 +6,13 @@ for _, x in pairs({8, 10, 11, 12, 13, 14, 17, 21, 29, 30}) do has_error_code[x] = true end +print("section .data") +print("idt_entries:") +for i = 0, 255 do + print("dq isr_"..i) +end + +print("section .text") for i = 0, 255 do print("isr_" .. i .. ":") print("cli") @@ -18,11 +25,6 @@ for i = 0, 255 do print("jmp isr_common") end -print("idt_entries:") -for i = 0, 255 do - print("dq isr_"..i) -end - print([[ isr_common: push r15 @@ -42,6 +44,7 @@ isr_common: push rax cld + xor rbp, rbp mov rdi, rsp call interrupt_handler diff --git a/stage3/main.c b/stage3/main.c index ae94abf..b796fd1 100644 --- a/stage3/main.c +++ b/stage3/main.c @@ -63,6 +63,12 @@ void kmain() heap_init(); #define MMAP for (MemRegion *mreg = (void *) 0x500; mreg->start != nil; mreg++) + MMAP { + if (mreg->start == (void *) 0x100000) { + mreg->start = (void *) 0x200000; + mreg->size -= 0x100000; + } + } // backup memory map usize n_mreg = 0; diff --git a/stage3/paging.asm b/stage3/paging.asm index 783649e..f58bb98 100644 --- a/stage3/paging.asm +++ b/stage3/paging.asm @@ -1,15 +1,24 @@ global page_region -section .text +%define PAGEBUFSIZE 0x10 * 0x1000 + +section .bss + +ALIGN(4096) +pagebuf_data: resb PAGEBUFSIZE + +section .data pagebuf_init: - .start: dq 0x5000 - .size: dq 0x2000 + .start: dq pagebuf_data + .size: dq PAGEBUFSIZE .used: dq 0 pagebuf: dq pagebuf_init next_page: dq 0 +section .text + ; allocate new page table buffer alloc: ; rsi = buffer (result) diff --git a/stage3/watchdog.lua b/stage3/watchdog.lua index dac4d57..8d3a206 100644 --- a/stage3/watchdog.lua +++ b/stage3/watchdog.lua @@ -12,9 +12,13 @@ local regs = { print("global watchdog") print("extern rand, watchdog_err") +print("section .bss") + print("regs_backup: resq 16") print("regs_rand: resq 16") +print("section .text") + print("watchdog:") local function iter_regs(f) |