我有一个基本的引导程序,应该从FAT12格式的软盘读取根扇区到内存中。 (该部分有效)但在实施之后它停止将字符写入屏幕。上次这样做是因为我忘记了POP寄存器。 但我已经三次检查了我是否已经将每个注册回归。
我还使用了BOCHS调试器,并根据它到达终点并执行打印字符命令。
我现在被困住了。如果有人能看一下我的代码,我真的很开心。
这是我的代码:
org 0x7c00
bits 16
start: jmp loader
;OEM
TIMES 0Bh-$+start DB 0
bpbBytesPerSector: DW 512
bpbSectorsPerCluster: DB 1
bpbReservedSectors: DW 1
bpbNumberOfFATs: DB 2
bpbRootEntries: DW 224
bpbTotalSectors: DW 2880
bpbMedia: DB 0xF0
bpbSectorsPerFAT: DW 9
bpbSectorsPerTrack: DW 18
bpbHeadsPerCylinder: DW 2
bpbHiddenSectors: DD 0
bpbTotalSectorsBig: DD 0
bsDriveNumber: DB 0
bsUnused: DB 0
bsExtBootSignature: DB 0x29
bsSerialNumber: DD 0xa0a1a2a3
bsVolumeLabel: DB "MOS FLOPPY "
bsFileSystem: DB "FAT12 "
;vars
absoluteSector db 0x00
absoluteHead db 0x00
absoluteTrack db 0x00
;functions
print:
xor bx, bx
lodsb
cmp al, 00h
je print_eof
mov ah, 0eh
int 10h
jmp print
print_eof:
ret
;************************************************;
; Convert LBA to CHS
; AX=>LBA Address to convert
;
; absolute sector = (logical sector / sectors per track) + 1
; absolute head = (logical sector / sectors per track) MOD number of heads
; absolute track = logical sector / (sectors per track * number of heads)
;
;************************************************;
lbachs:
xor dx, dx ; prepare dx:ax for operation
div WORD [bpbSectorsPerTrack] ; calculate
inc dl ; adjust for sector 0
mov BYTE [absoluteSector], dl
xor dx, dx ; prepare dx:ax for operation
div WORD [bpbHeadsPerCylinder] ; calculate
mov BYTE [absoluteHead], dl
mov BYTE [absoluteTrack], al
ret
ReadSectors:
push ax ;safety
push bx ;safety
push cx ;safety
call lbachs ;change LBA to CHS (floppy)
mov ah, 0x02 ;function to read sector from floppy
mov al, 0x01 ;read only 1 sector
mov ch, [absoluteTrack] ;at track X
mov cl, [absoluteSector];at sector X
mov dh, [absoluteHead] ;at had X
mov dl, 0x00 ;on drive 00 (floppydrive
int 0x13 ;execute
jnc .succes ;if succeeded goto succes else:
mov ah, 0x00 ;reset floppy drive
mov bl, 0x00 ;drive 0
int 0x13 ;execute
pop cx ;pop
pop bx
pop ax
jmp ReadSectors ;retry
.succes:
pop cx ;pop
pop bx
pop ax
add bx, WORD [bpbBytesPerSector] ;next 512 bytes in memory to write sector to
inc ax ;next sector
LOOP ReadSectors ;and keep looping till cx == 0
ret ;return
;Bootloader
loader:
mov si, msg
call print
xor cx, cx
mov ax, 0x0020 ; 32 byte directory entry
mul WORD [bpbRootEntries] ; number of root entrys
div WORD [bpbBytesPerSector] ; get sectors used by root directory
xchg cx, ax ;;cx=LENGTH in sectors
mov al, [bpbNumberOfFATs] ; Get number of FATs (Useually 2)
mul WORD [bpbSectorsPerFAT] ; number of FATs * sectors per FAT; get number of sectors
add ax, [bpbReservedSectors] ; add reserved sectors
;AX=START as sector in LBA (so needs conversion
mov bx, 0x0200 ; load root directory to 7c00:0x0200
call ReadSectors
mov cx, [bpbRootEntries] ; the number of entrys. If we reach 0, file doesnt exist
mov di, 0x0200 ; Root directory was loaded here
.LOOP:
push cx
mov cx, 11 ; eleven character name
mov si, imageName ; compare the 11 bytes with the name of our file
push di
rep cmpsb ; test for entry match
pop di
je LOAD_FAT ; they match, so begin loading FAT
pop cx
add di, 32 ; they dont match, so go to next entry (32 bytes)
loop .LOOP
jmp FAILURE ; no more entrys left, file doesnt exist :(
LOAD_FAT:
mov bh, 00h ;page to wwrite to.
mov ah, 0eh ;write character
mov al, 'Y' ;write the Y character
int 10h ;execute
jmp EoF ;jump to end of file
FAILURE:
mov bh, 00h ;page to write to
mov ah, 0eh ;write character
mov al, 'N' ;write the N character
int 10h ;execute
EoF:
mov bh, 00h ;see above :P
mov ah, 0eh
mov al, 'D'
int 10h
cli
hlt
streof db 'DONE....',0x0A, 0x0D, 00h
msg db 'Hello!', 0x0D, 0x0A, 00h
msg2 db 'Done reading root directory!', 0x0D, 0x0A, 00h
succ db 'YES file is found!', 00h
fil db 'Failed no file found!', 00h
imageName db "KRNLDR SYS"
times 510 - ($-$$) db 0
dw 0xAA55
提前致谢。
的 -Tim 的
PS: (对于那些说我不应该复制代码的人) 我只复制了检查文件是否存在的问题'来自breaknthorn的代码,看看我是否正确加载了ROOT。
答案 0 :(得分:0)
我修好了。
在搜索并询问irc后,我得出的结论是我没有正确设置堆栈寄存器。我将org 0x7c00
更改为org 0
,然后跳转到加载程序(loader:
)后,我正确地输入了堆栈:
cli
mov ax, 0x07c0
mov ds, ax
mov es, ax
mov fs, ax
mov gs, ax
mov ax, 0x0000
mov ss, ax
mov sp, 0xFFFF
sti
我希望这可以帮助那些有同样问题的人!
的 -Tim 强> 的