From 89e2cef4fab4ed3fb5f13946e039abcb1aceec28 Mon Sep 17 00:00:00 2001 From: pantonshire Date: Fri, 19 Jul 2024 09:05:13 +0100 Subject: [PATCH] start work on panic handler --- boot1.s | 150 +++++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 104 insertions(+), 46 deletions(-) diff --git a/boot1.s b/boot1.s index 3cf47b4..8077dba 100644 --- a/boot1.s +++ b/boot1.s @@ -216,9 +216,9 @@ main: mov ax, msg_boot1_loaded call vga_println - mov ecx, 0xa1b2c3d4 - call vga_dump_reg - hlt + mov eax, 0xa1b2c3d4 + mov ebx, 0x12345678 + call panic_fancy call test_a20 test ax, ax @@ -252,14 +252,50 @@ panic_default: ; Print a panic message then terminate. ; Arguments: -; - [sp - 2]: pointer to panic message -; - [sp]: panic message length +; - [sp - 2]: panic message segment +; - [sp]: panic message offset ; Does not return panic_fancy: push bp mov bp, sp + + sub sp, 16 ; Buffer: bp - 16 + + push eax ; bp - 20 + push ebx ; bp - 24 + push ecx ; bp - 28 + push edx ; bp - 32 + push esi ; bp - 36 + push edi ; bp - 40 + mov word [GLOBALS + VGA_COL], 0x4f00 + call vga_clear + + mov ax, ss + mov es, ax + + lea ax, [bp - 16] + push ax + mov ecx, [bp - 20] + call dump_reg + pop cx + xor ax, ax + mov dx, 8 + call vga_print_raw + + lea ax, [bp - 16] + push ax + mov ecx, [bp - 24] + call dump_reg + pop cx + mov ax, VGA_WIDTH + mov dx, 8 + call vga_print_raw + +.halt: hlt + ; Handle non-maskable interrupts + jmp .halt ; Clear the VGA text buffer. @@ -334,40 +370,42 @@ vga_scroll: fnret -; Write one line to the VGA text buffer. The string should be null-terminated; we embrace the evil -; of null-termination so this function only takes one argument, so it's slightly less of a faff to -; call in most cases. +; Write a null-terminated string to the given position in the VGA text buffer. ; Arguments: ; - es: output string segment -; - ax: output string offset -; Return: none -; Clobber: ax -vga_println: +; - ax: vga buffer index +; - cx: output string offset +; - dx: maximum length of string to print +; Return: +; - ax: vga buffer index after last character written +; Clobber: none +vga_print_raw: fnstart + push fs push si push di + push cx push dx - push fs - - cmp word [GLOBALS + TEXTBUF_LINE], VGA_HEIGHT - jb .scroll_done - call vga_scroll -.scroll_done: - - mov si, ax - - xor dx, dx - mov ax, [GLOBALS + TEXTBUF_LINE] - mov di, VGA_WIDTH * 2 - mul di - mov di, ax + mov si, cx + xchg ax, cx + + ; Find the distance between the starting index and the end of the buffer. + mov ax, (VGA_WIDTH * VGA_HEIGHT) + sub ax, cx + ; If the starting index is past the end of the buffer, return early. + jc .done + ; Clamp the maximum length to the distance between the starting index and the end of the buffer. + cmp ax, dx + cmovb dx, ax + + mov di, cx + shl di, 1 + mov ax, 0xb800 mov fs, ax mov ah, [GLOBALS + VGA_COL + 1] - mov dx, VGA_WIDTH - .loop: test dx, dx jz .done @@ -378,38 +416,58 @@ vga_println: mov fs:[di], ax add di, 2 inc si - dec cx + inc cx jmp .loop - + .done: - inc word [GLOBALS + TEXTBUF_LINE] - - pop fs + xchg ax, cx + pop dx + pop cx pop di pop si + pop fs fnret -vga_dump_reg: +; Write one line to the VGA text buffer. The string should be null-terminated; we embrace the evil +; of null-termination so this function only takes one argument, so it's slightly less of a faff to +; call in most cases. +; Arguments: +; - es: output string segment +; - ax: output string offset +; Return: none +; Clobber: none +vga_println: fnstart - sub sp, VGA_WIDTH - push es + push ax push bx + push cx + push dx + + cmp word [GLOBALS + TEXTBUF_LINE], VGA_HEIGHT + jb .scroll_done + call vga_scroll +.scroll_done: - mov ax, ss - mov es, ax - lea ax, [bp - VGA_WIDTH] - call dump_reg mov bx, ax - mov byte es:[bx], 0 + + xor dx, dx + mov ax, [GLOBALS + TEXTBUF_LINE] + mov cx, VGA_WIDTH + mul cx - lea ax, [bp - VGA_WIDTH] - call vga_println + mov dx, VGA_WIDTH + mov cx, bx + + call vga_print_raw + + inc word [GLOBALS + TEXTBUF_LINE] - pop bx - pop es - add sp, VGA_WIDTH + pop dx + pop cx + pop bx + pop ax fnret