在64位Ubuntu上,我编写了一个加载内核的引导程序,它提供了一个echo程序(输出输入的内容):
Bootloader代码:
[BITS 16]
org 0x7C00
bootdrive db 0
start:
mov [bootdrive], dl
mov ah, 0
int 13h
mov dx, 0
mov ah, 2
mov al, 0x10
mov dl, [bootdrive]
mov ch, 0
mov dh, 0
mov cl, 2
mov bx, 0
int 13h
jmp 0x1000:0000
times 510-($-$$) db 0
dw 0xAA55
内核代码:
[BITS 64]
call _stdin
jmp $
_stdin:
mov ah, 0
int 16h
mov ah, 0eh
mov bx, 0
int 10h
ret
int 16h / ah = 0接受输入并将缓冲区放入al。然后,我试图通过int 10h / al = 0eh打印al,但它没有通过。我甚至试过把
mov al, "!"
介于
之间 mov ah, 0eh
和
mov bx, 0
但它似乎不喜欢16h中断。我还尝试使用int 21h(ah = 8,ah = 1,ah = 0ah)的各种其他stdin命令,但它们都没有能够读取击键。我会键入一个键并按ENTER键,但不会发生任何事情。更令人困惑的是,即使int 21h(ah = 02h)内的输出命令也没有打印任何东西。我尝试将内核切换到实模式(32位)而不是长模式(64位),但是int 21h仍然无法工作。为了清楚起见,我希望能够在不等待返回键击的情况下读取键盘输入,这样我就可以在调用输入中断和执行其他进程之间进行切换。 int 21h似乎没有工作,甚至在32位模式下也没有工作,以及int 16.我实际上唯一工作的中断是int 10h和int 13h(在代码中显示),但是其他的中断不包括#39;因某种原因而工作。
注意: 我使用nasm bootloader.asm -p kernel.asm组装了bootloader和内核来创建一个名为bootloader的bin文件,我使用qemu-system-x86_64来运行汇编的bin文件。
答案 0 :(得分:0)
[EDITED]
这是我写的一个包含引导加载程序和内核的程序,它在转换为.iso文件时有效:
[BITS 16]
org 0x7C00
mov ax, 0
mov es, ax
mov ah, 2
mov al, 1
mov ch, 0
mov dh, 0
mov cl, 2
mov bx, _stage2
int 0x13
jmp _stage2
times 510-($-$$) db 0
dw 0xAA55
_stage2:
call _stdin
call _stdout
jmp _stage2
_stdin:
mov ah, 1
mov al, 0
int 16h
cmp al, 0
je _stdin
mov ah, 0
int 16h
ret
_stdout:
mov ah, 0eh
mov bx, 0
int 10h
ret