%define KBDINT 0x16
%define VIDINT 0x10
%define DISKINT 0x13
%define TTYOUT 0x0E
%define VIDMODE 0x0000
%define NUL 0x00
%define CR 0x0D
%define LF 0x0A
%define START 0x7C00
%macro PRINT 1
mov si, %1
call print
%endmacro
bits 16 ; 16 bit real mode
org START ; loader start in memory
start: jmp main
print: jmp .init
.loop: mov bx, VIDMODE
mov ah, TTYOUT
int VIDINT
inc si
.init: mov al, [si]
cmp al, NUL
jne .loop
ret
main: cli
xor ax, ax
mov ds, ax
mov es, ax
sti
PRINT welcome
mov ah, NUL
int DISKINT
mov al, 0x01 ; sector count
mov ah, 0x02 ; read function
mov bx, kernel
mov cl, 0x02
mov ch, 0x00 ; cylinder number
mov dh, 0x00 ; head number
int DISKINT
jc fail
jmp kernel
fail: PRINT failure
; jmp halt
halt: PRINT halting
cli
hlt
PRINT imprbbl
jmp halt
welcome db "moose os", CR, LF, NUL
failure db "failed disk load", CR, LF, NUL
halting db "halting", CR, LF, NUL
imprbbl db "but that's impossible!", CR, LF, NUL
times 0x0200 - ($ - $$) - 2 db 0x00
end dw 0xAA55
kernel: PRINT yay
yay db "kernel", CR, LF, NUL
jmp halt
times 0xFFFF db 0x00
我用以下命令编译文件:
nasm -f bin -o boot.bin boot.asm && qemu boot.bin
,然后执行二进制文件。如下图所示:
- 磁道是如何遍历的?
- 在模拟和直接执行之间如何不同?
jmp halt
放在yay db "kernel", CR, LF, NUL
之前。现在你执行的是垃圾代码,这是一件危险的事情! - Fifoernik