I am working on a custom 32-bit OS, and i have coded a bare bones bootloader. I am trying to make it load a simple kernel that puts a char onto the screen, however, instead of getting the char i get a triple fault (maybe?)
I've tried increasing the ammount of sectors read, the ammount of 'db 0's in my extended program, tampering with the compilation script... Nothing, however, my OS also prints the letter 'H' if it succeeds to read the disk, and sometimes when i increase the ammount of sectors to something exponential, the vm doesnt restart, but the disk isnt read successfully.
Github: https://github.com/Nutty000/Broken-OS
CodePudding user response:
"BROKEN-OS", you say?
Your GitHub ldr.asm file has many errors.
The Boot Sector and BPB Structure uses all the wrong data sizes! No wonder your VM gets all confused.
should be
---------
OEMIdentifier db "POSv0.10"
BytesPerSector dd 512 DW
SectorsPerCluster db 1
ReservedSectors db 32 DW
NumberOfFATs db 2
NUmberOfRootDirEntries db 224 DW
NumberOfSectors dd 2880 DW
MediaDescriptorType db 0xf0
SectorsPerFAT db 9 DW
SectorsPerTrack db 18 DW
NumberOfSides db 2 DW
HiddenSectors db 0 DD
LargeSectorCount db 0 DD
DriveNumber db 0x00
db 0
Signature db 0x29
VolumeID db 0x00, 0x00, 0x00, 0x00
VolumeLabel db "POSBOOTDSK "
SystemIdentifier db "FAT12 "
jmp short mbrcodestart
This short jump is encoded with 2 bytes, but the above mentioned structure must begin at offset 3 in your bootsector. You need to pad with a nop
instruction, or force a near
(non-short) jmp.
jmp short mbrcodestart
nop
The fact of storing a capital "H" as the first byte of your [ExtendedSpace] that you later jump to was a bad idea, but luckily for you that will not pose a problem as that particular encoding 72 happens to correspond to a valid one-byte instruction dec ax
.
There's also:
- not setting up the segment registers yourself
- not setting up a stack in a safe place where the additional sectors can't overwrite it
- ignoring the
BH
andBL
parameters of the BIOS.Teletype call - not inspecting the carry flag that you get from the
int 13h
call - reading many sectors at once instead of the more reliable method of using a loop of reading individual sectors. (Some real-world BIOSes are somewhat broken; using only the simplest functionality will let your bootloader work even on such machines. See also Michael Petch's general tips for bootloaders.)
- ...
All of this happens even before diving into protected mode. First make sure the real mode part works fine before attempting to go further.
There are many good answers on this forum that deal with these issues:
Bootloader doesn't jump to kernel code
My OS is showing weird characters
Your current ldr.asm for reference:
[org 0x7c00]
jmp short mbrcodestart
OEMIdentifier db "POSv0.10"
BytesPerSector dd 512
SectorsPerCluster db 1
ReservedSectors db 32
NumberOfFATs db 2
NUmberOfRootDirEntries db 224
NumberOfSectors dd 2880
MediaDescriptorType db 0xf0 ;3.5 Inch Double-Sided HD Floppy disk(1.44MB or 2.88MB) should work with single-sided ones as well, maybe even 5.25 inch diskettes
SectorsPerFAT db 9
SectorsPerTrack db 18
NumberOfSides db 2
HiddenSectors db 0
LargeSectorCount db 0
;EBPB
DriveNumber db 0x00 ;Floppy Disk
db 0 ;Reserved
Signature db 0x29
VolumeID db 0x00, 0x00, 0x00, 0x00
VolumeLabel db "POSBOOTDSK "
SystemIdentifier db "FAT12 "
mbrcodestart:
mov bx, POSBL_WelcomeString
call print16
call read16
mov ah, 0x0e
mov al, [ExtendedSpace]
int 0x10
jmp ExtendedSpace
POSBL_WelcomeString:
db "PlanetOS BootLoader (POSBL) v0.1 (limited compatability)",0
print16:
mov ah, 0x0e
loop:
mov al, [bx]
cmp al, byte 0
je exit
int 0x10
inc bx
jmp loop
exit:
ret
ExtendedSpace equ 0x7e00
read16:
mov ah, 0x02
mov al, 20
mov bx, ExtendedSpace
mov ch, 0x00
mov cl, 0x02
mov dh, 0x00
mov dl, 0x00
int 0x13
ret
times 510-($-$$) db 0
dw 0xaa55
CodePudding user response:
The first instruction executed after jmp ExtendedSpace
is db 'H'
i.e. not code