Hallo,
Erst mal ein dickes Lob an das ganze LOWLEVEL-Team, ich finde es super das Magazin und die ganze Seite einfach super. Jetzt aber zu meinem Problem:
Ich habe (versucht) einen eigenen Bootloader zu schreiben, der die Datei Kernel.sys von einer Diskette (das ganze basiert also auf FAT12) nach 0x1000:0000 lesen und anschließend ausführen soll. Bis zur Ausgabe des Ladestrings funktioniert auch alles, ab dann aber leider nicht mehr. Ich hoffe jemand von euch sieht den Fehler.
Ich benutze übrigens FASM.
Erst mal ein dickes Lob an das ganze LOWLEVEL-Team, ich finde es super das Magazin und die ganze Seite einfach super. Jetzt aber zu meinem Problem:
Ich habe (versucht) einen eigenen Bootloader zu schreiben, der die Datei Kernel.sys von einer Diskette (das ganze basiert also auf FAT12) nach 0x1000:0000 lesen und anschließend ausführen soll. Bis zur Ausgabe des Ladestrings funktioniert auch alles, ab dann aber leider nicht mehr. Ich hoffe jemand von euch sieht den Fehler.
Code: [Auswählen]
org 0h;;;;;;;;;7c00h
jmp buildstack
nop
;Fat12 "Header"
OSName db "LearnOS "
BytesPerSec dw 0200h
SecPerClus db 1
RsvdSecCnt dw 1
NumFATs db 2
RootEntCnt dw 224d
TotSec dw 2880d
MediaType db 0f0h
FATSize dw 9
SecPerTrack dw 12h
NumHeads dw 2
HiddenSec dd 0
TotSec32 dd 0
DrvNum db 0
Reserved db 0
BootSig db 29h
VolumeID dd 0
VolumeLable db "NO NAME "
FileSysType db "FAT12 "
buildstack: ;wir bauen einen Stack
jmp 7c0h:43h ;Da ist der Bootloader aber mit cs = 7c0 ist es nachher leichter Sachen einzulesen
cli
push cs
pop ss
mov sp,0ffffh
sti
push cs
push cs
pop ds
pop es
mov si,loadmsg ;Ladestring ausgeben
mov ah,0eh
nextchar:
lodsb
or al,al
jz lenoffat
int 10h
jmp nextchar
mov byte [DrvNum],dl
lenoffat:
mov ax,word [FATSize]
mul word [BytesPerSec]
mov word [LenOfFAT],ax
posofroot: ;Berechnung der Position (LBA) des Root-dirs
mov al,byte [NumFATs];so viele FAT-Tabellen haben wir
mul word [FATSize] ;so groß ist eine
add ax,word [RsvdSecCnt];und soviele Sektoren befinden sich vor ihr
push ax
initdrv:
mov ah,0 ;Laufwerk initialisieren
mov dl,byte [DrvNum]
int 13h
jc initdrv
mov bx,200h ;Lesen nach es:bx
readfat:
mov ah,2
mov al,byte [FATSize];mal angenommen, dass niemand eine FAT-Tabelle größer als 255 Sektoren macht ;-)
xor cx,cx ;Track (Zylinder) 0
inc cl ;Sektor 1
xor dx,dx ;von Head 0
int 13h
jc readfat
readroot: ;Sektoren des Root-directorys lesen (14)
pop ax
call lba2chs
mov ax,020eh
mov bx,word [LenOfFAT];haben wir bei lenoffat berechnet
mov dl,byte [DrvNum]
int 13h
jc readroot
mov si,bx ;Länge der FAT-Tabelle (Position des Root-dir)
searchroot:
mov cx,11 ;so lang sind die Dateinamen
mov di,KernelName ;und so heißt der Kernel
push si
repe cmpsb ;repeat if equal
pop si
je readinkernel
add si,20h ;nächster Eintrag
jmp searchroot
readinkernel:
mov ax,1000h ;dahin kommt nachher der Kernel (es:bx)
mov es,ax
xor bx,bx
mov si,[si + 1ah] ;ab Offset 1a innerhalb eines Eintrags steht der Anfangssektor
extractfatentry:
mov ax,[si] ;nach ax kommt jetzt der FAT-Eintrag
parsefatentry:
test ax,1
jz evensector
shr ax,4
evensector:
and ax,0fffh
push ax
add ax,word [RsvdSecCnt]
call lba2chs
mov ax,0201h
mov dl,byte [DrvNum]
int 13h
add bx,200h
pop ax
cmp ax,0fffh ;das bedeutet, dies ist der letzte Cluster der Datei
je jmp2kernel
mov si,ax
jmp extractfatentry
jmp2kernel:
jmp 1000h:0000h
lba2chs: ;das Label sagt alles (Quelle: http://www.all-science-fair-projects.com/science_fair_projects_encyclopedia/CHS_conversion)
xor dx,dx
div word [SecPerTrack];in ax war die LBA-Adresse
inc dl ;der Rest der Division ist der Sektor - 1
mov cl,dl
xor dx,dx
div word [NumHeads] ;der Rest ist der Head und der Quotient ist der Track (Zylinder)
mov dh,dl
mov ch,al
ret
loadmsg db "Starting LearnOS...",0dh,0ah,0
LenOfFAT dw ?
KernelName db "KERNEL SYS"
rb 510d - ($ - $$)
dw 0aa55h
Ich benutze übrigens FASM.

Übersicht
Wiki
Hilfe
Suche
Einloggen
Registrieren
Drucken

Gespeichert