Implement whacky first version for 25h disk read

This commit is contained in:
Nero 2020-04-26 23:14:34 +02:00
parent 43e5cd6379
commit 2d949a01f8

View File

@ -4,6 +4,19 @@
%include "inc/bpb.asm"
; Far call via interrupt vector
%macro intcall 1
call far [cs:%1*4]
%endmacro
; Far jump via interrupt vector
%macro intjump 1
jump far [cs:%1*4]
%endmacro
; stack size
%define stacks 512
banner: db "rdos", 0xA, 0xD, '$'
; Alias for Int 21h,AH=0h
@ -26,7 +39,7 @@ int21h: ; inside of kernel, direction always goes up
; do the actual subfunction call
call [cs:sfptr]
; inherit the lower 8 flag bits to userspace
push ax
iretfl: push ax
push bp
mov bp, sp
lahf
@ -239,7 +252,105 @@ ldbpb: push ds
pop ds
ret
; DOS 2+ - DOS IDLE INTERRUPT
; defines for CHS table
chs_spt: equ 0 ; word sectors per track
chs_nos: equ 2 ; word number of sides
chs_po: equ 4 ; dword partition offset
chs_siz: equ 8
fndchs: ; find CHS table entry
; IN dl DOS drive number (A=0, B=1, ...)
; OUT cs:si ptr to chs table entry
push ax
mov ax, chs_siz
mul dl
add ax, chstab
mov si, ax
pop ax
ret
; compare sector number in disk access packet with zero
; sets zero flag accordingly
iszero: push ax
mov ax, [bx]
or ax, [bx+2]
pop ax
ret
; calculate CHS from dap and CHS table entry
; IN ds:bx disk access packet
; cs:si chstab table entry
; OUT cx,dh chs data for int 13h
calchs: push ax
; load linear sector number
mov dx, [bx+2]
mov ax, [bx]
; if any word of it is non-zero, we need to do calculation
call iszero
jz .zero
; ax is track number (lba / spt)
; dx is sector (lba % spt) + 1
div word [cs:si+chs_spt]
inc dx
; sector number
mov cl, dl
; ax is cylinder (track / heads)
; dx is head (track % heads)
xor dx, dx
div word [cs:si+chs_nos]
; set up cylinder and head number
mov ch, al
mov dh, dl
pop ax
ret
; set up CHS data for int 13h for reading sector zero
.zero: mov cx, 1 ; C=0, S=1
mov dh, 0 ; H=0
pop ax
ret
; ABSOLUTE DISK READ / DISK WRITE
int25h: mov ah, 2
jmp adisk
int26h: mov ah, 3
adisk: push bp
push ds
push es
mov bp, sp
cmp cx, 0xFFFF
je .islrg
; build a disk access packet on the stack
push ds ; dword transfer buffer
push bx
push cx ; word number of sectors
push cs ; dword starting sector number (CS always 0)
push dx
; set our freshly created dap as DS:BX
mov bx, sp
push ss
pop ds
.islrg: mov dl, al
call fndchs
call calchs
mov dl, al
mov al, [bx+4]
mov es, [bx+8]
mov bx, [bx+6]
int 0x13
jc .ret
.ret: mov sp, bp
pop es
pop ds
pop bp
retf: retf
; DOS IDLE INTERRUPT
; Usually hooked by TSRs
idle: sti
; sti takes one instruction to take effect
@ -248,7 +359,7 @@ idle: sti
hlt
iret
; DOS 2+ - FAST CONSOLE OUTPUT
; FAST CONSOLE OUTPUT
; IN al character to print
fputc: push ax
push bx
@ -259,36 +370,42 @@ fputc: push ax
pop ax
iret
; write CS:AX to ES:DI and advance DI
; used for setting interrupts
stovec: stosw
vects: dw int20h, int21h, retf, retf
dw retf, int25h, int26h, int20h
dw idle, fputc
main: ; zero out first 64kb except our code
; bss and boot sector area gets cleared by this
mov di, init
mov cx, di
neg cx
xor ax, ax
rep movsb
; install interrupt vectors
mov si, vects
mov di, (0x20*4)
mov cx, 0x0A
intlp: movsw
mov ax, cs
stosw
ret
vects: dw int20h, int21h, idle, fputc
main: mov si, vects
mov di, (0x20*4)
lodsw
call stovec
lodsw
call stovec
mov di, (0x28*4)
lodsw
call stovec
lodsw
call stovec
loop intlp
; print banner to indicate we are booted
mov si, banner
mov ah, 9
int 0x21
call dnconv
mov al, dl
mov cx, 1
mov dx, 0
mov bx, buffer
int 3
intcall 0x25
int 3
loop: int 0x28
mov ah, 7
int 0x21
jz loop
int 0x29
jmp loop
init: cli
@ -296,7 +413,7 @@ init: cli
mov ds, ax
mov es, ax
mov ss, ax
mov sp, stacke
mov sp, ( stack+stacks )
; relocate
mov si, 0x7C00
@ -307,11 +424,15 @@ init: cli
jmp 0:main
section .bss
; stack to be used during init and disk i/o
stack: resw stacks
; default int 25h/26h handler use a cache to keep geometry for
; the first 4 drives
chstab: resw (4*chs_siz)
bpb: resb bpb_len
drvnum: resb 1
align 4
drvoff: resd 1; partition offset
drvpos: resd 1; absolute physical sector number
buffer: resb 512
stack: resw 512
stacke: