x86_fat12bs/src/stage3.asm

141 lines
2.2 KiB
NASM

org 0x10000 ; 64k this is terrible but IDC
%include "addr.inc"
%macro print_msg 1
mov eax, %1
push eax
call print_str
add esp, 4
%endmacro
%macro print_rtn 0
mov eax, 0xA
call print_char
%endmacro
%macro print_addr 2
push %1
call print_u32
add esp, 4
mov eax, 0x3A ; colon
call print_char
push %2
call print_u32
add esp, 4
%endmacro
[SECTION .text]
[BITS 32]
jmp start
%include "print32.lib"
start:
mov dword [vb_pos], ebx ; ebx holds framebuffer pointer
print_msg msg_ok
print_rtn
print_msg msg_switch_gdt_pre
; switch stack and GDT
lgdt [gdtr32]
jmp dword gdt32.sel_code:.reload
.reload:
mov ax, gdt32.sel_data
mov ds, ax
mov ss, ax
mov es, ax
mov gs, ax
mov fs, ax
mov esp, stack
print_msg msg_ok
print_rtn
print_msg msg_init_idt
; write offset to idt
mov eax, dummy_handler
mov word [idt32], ax
mov cl, 16
shr eax, cl
mov word [idt32 + 6], ax
lidt [idtr32]
print_msg msg_ok
print_rtn
print_msg msg_test_div
xor ax, ax
div ax
next_op:
print_msg msg_ok
print_rtn
print_msg msg_init_krnl
mov eax, KERNEL_FLAT
jmp eax
err:
print_msg msg_err
jmp $
dummy_handler:
print_msg msg_div
call print_u32 ; top of stack is the address
print_msg msg_space
mov dword [esp], next_op ; overwrite return address
iretd
[SECTION .data]
[BITS 32]
msg_div: db '#DIV at ', 0
msg_space: db ' ', 0
msg_ok: db 'OK ', 0
msg_err: db 'ERR ', 0
msg_switch_gdt_pre: db 'Reloading GDT and stack... ', 0
msg_init_idt: db 'Initializing IDT... ', 0
msg_test_div: db 'Testing #DIV exception... ', 0
msg_init_krnl: db 'Jumping to kernel... ', 0
align 4096
times 4096 db 0
stack:
align 16
idt32:
dw 0 ; offset low 16 bits
dw gdt32.sel_code ; selector
db 0
db 0b10001111 ; Present | DPL 0 | Trap gate
dw 0
.size equ $ - idt32
idtr32:
dw idt32.size - 1
dd idt32
align 16
gdt32:
dd 0
dd 0
.sel_code: equ $ - gdt32
dw 0xFFFF ; LIMIT = 0xFFFF
dw 0 ; BASE LOW = 0
db 0 ; BASE MID = 0
db 10011010b; PRESENT | RW | EXE
db 11001111b; Granularity = 4k | 32 bits
db 0 ; BASE_HIGH = 0
.sel_data: equ $ - gdt32
dw 0xFFFF ; LIMIT = 0xFFFF
dw 0 ; BASE LOW = 0
db 0 ; BASE MID = 0
db 10010010b; PRESENT | RW | EXE
db 11001111b; Granularity = 4k | 32 bits
db 0 ; BASE_HIGH = 0
.size: equ $ - gdt32
align 16
gdtr32:
dw gdt32.size - 1
dd gdt32