Revamp MBR

New features:
- ES:DI (potential PnP structure) is preserved
- FAT detection now works by checking for BPB values
- Uses booterr procedure
This commit is contained in:
Nero 2020-04-21 23:23:37 +02:00
parent bbfcd42f61
commit abc7b563cd

View File

@ -1,136 +1,142 @@
; Memory layout:
%define self 0x00600 ; 1 sector
%define prog 0x07C00 ; 1 sector
; FDC fields in VBR ; FDC fields in VBR
%define spt (prog + 0x18) %define bps (bs + 0x0B)
%define nos (prog + 0x1A) %define md (bs + 0x15)
%define po (prog + 0x1C) %define spt (bs + 0x18)
%define nos (bs + 0x1A)
%define po (bs + 0x1C)
org self ; blah dont judge me, i miss 8080
cpu 8086 %macro retnz 0
jz short ($+3)
ret
%endmacro
%macro callc 1
jnc short ($+5)
call %1
%endmacro
init: cpu 8086
cli org 0x0600
bs: equ 0x7C00
; Stack grows down from PSP + 64k init: cli
xor ax, ax xor ax, ax
mov ss, ax mov ss, ax
mov sp, ax xor sp, sp
push dx ; save driver number
push dx
; Relocate from [prog] to [self] ; save PnP ptr
mov ds, ax push es
mov es, ax push di
mov si, prog
mov di, self
mov cx, 0x100
rep movsw
jmp 0:main ; Relocate away from bootsector loading area
mov ds, ax
mov es, ax
mov si, bs
mov di, $$
mov cx, 0x100
rep movsw
main: jmp 0:main
mov bp, 0x3335
mov si, part1
mov cx, 4
.loop:
test BYTE [si], 0x80
jnz loadpart
add si, 0x10
loop .loop
jmp error
loadpart: %include "inc/booterr.asm"
; transfer starting address into DAP
push si
add si, 0x08
mov di, dap.blocknum
movsw
movsw
pop si
; load sector ; find active partition or bail out
push si ; result in si
mov si, dap findp: mov si, part1
mov bp, 0x3336 mov cx, 4
mov ah, 0x42 .loop: test BYTE [si], 0x80
stc retnz
int 0x13 add si, 0x10
jc error loop .loop
pop si call errcll
cmp BYTE [si+4], 0x01 main: ; find active partition
jne jump call findp
adjust: ; transfer starting address into DAP
push dx push si
add si, 0x08
mov di, dap.num
movsw
movsw
pop si
mov bp, 0x3337 ; load sector
mov ah, 0x08 push si
stc mov si, dap
int 0x13 mov ah, 0x42
jc error stc
int 0x13
callc errcll
pop si
; update sectors per track ; FAT bpb has "bytes per sector" at this place
xor ax, ax ; we support only 512 byte sectors anyways
mov al, cl cmp word [bps], 512
mov [spt], ax jne chain
; update number of sides ; Media descriptor byte is never smaller than 0xF0
xor ax, ax cmp byte [md], 0xF0
mov al, dh jc chain
mov [nos], ax
; update partition offset ; ask BIOS what our disk geometry is
push si mov ah, 0x08
add si, 0x08 stc
mov di, po int 0x13
movsw jc chain
movsw
pop si
pop dx ; ES might be messed up from int 13h, fix it
push cs
pop es
jump: ; update sectors per track
jmp 0:prog xor ax, ax
mov al, cl
mov [spt], ax
error: ; update number of sides
mov ax, bp xor ax, ax
mov ah, 0x0e mov al, dh
mov bx, 7 mov [nos], ax
int 0x10
mov al, 0x21 ; update partition offset
int 0x10 push si
xor ax, ax add si, 0x08
int 0x16 mov di, po
int 0x19 movsw
movsw
pop si
chain: ; restore PnP structure
pop di
pop es
pop dx
xor cx, cx
mov bp, si
; chain into partition boot sector
jmp 0:bs
dap: dap:
.size: .size: db 0
db 0 db 0
db 0 .count: dw 1
.count: .buf: dw bs
dw 1 dw 0
.buffer: .num: dq 0
dw prog
dw 0
.blocknum:
dq 0
times (0x1BE - ($-$$)) db 0 times (0x1BE - ($-$$)) db 0
part1:
db 0x80
.chs_start:
db 0xFF, 0xFF, 0xFF
.type:
db 0x01
.chs_end:
db 0xFF, 0xFF, 0xFF
.begin:
dd 1
.end:
dd (FLOPPY * 2)
times (0x1FE - ($-$$)) db 0 part1: db 0x80
dw 0xAA55 db 0xFF, 0xFF, 0xFF
db 0x01
db 0xFF, 0xFF, 0xFF
dd 1
dd (FLOPPY * 2)
times (0x1FE - ($-$$)) db 0
; Boot signature
dw 0xAA55