Throw DOS api away, re-layout memory to fit CP/M model

This commit is contained in:
Nero 2019-09-29 08:52:00 +00:00
parent 2935d7ee6c
commit 56f9df5773
5 changed files with 57 additions and 210 deletions

View File

@ -1,13 +1,15 @@
; Memory layout: ; Memory layout:
%define self 0x00600 ; 1 sector %define segment 0x00100
%define fattab 0x01000 ; variable size
%define rootdir 0x06000 ; variable size %define self (0x7C00-(segment<<4)) ; 1 sector
%define config 0x07800 %define fattab (self+0x200) ; variable size
%define prog 0x07C00 %define rootdir 0x00100 ; variable size
%define prog 0x0F000 ; 4K at the end for OS
org self org self
jmp short init jmp short init
dw self
cluster_offset: cluster_offset:
dw 0 dw 0
@ -58,23 +60,16 @@ times (62 - ($-$$)) nop
init: init:
cli cli
jmp segment:main
; Stack grows down from 64k
xor ax, ax
mov ss, ax
mov sp, ax
; Relocate from [prog] to [self]
mov ds, ax
mov es, ax
mov si, prog
mov di, self
mov cx, 0x100
rep movsw
jmp 0:main
main: main:
; Stack grows down from 64k
mov ax, cs
mov ss, ax
mov sp, prog
mov ds, ax
mov es, ax
mov [fdc.drv], dl ; save drive number in fd mov [fdc.drv], dl ; save drive number in fd
sti sti
@ -110,31 +105,10 @@ main:
mov bp, 0x3332 mov bp, 0x3332
jc error jc error
; Load config file after kernel
push bx
mov ax, config_name
call load_file
pop bx
; Write a null byte after config file
mov BYTE [bx+di], 0
; Setup registers for kernel
xor ax, ax
; CX is size of config
mov cx, di
; DL is drive number
xor dx, dx
mov dl, [fdc.drv] mov dl, [fdc.drv]
; BX is offset of config
sub bx, prog
; the pointers are 0
xor bp, bp
xor si, si
xor di, di
; jump into kernel ; jump into kernel
jmp (prog>>4):0 jmp segment:prog
; Load a file into memory ; Load a file into memory
; IN AX pointer to 8.3 filename ; IN AX pointer to 8.3 filename
@ -260,8 +234,6 @@ error:
int 0x16 int 0x16
int 0x19 int 0x19
config_name:
db "RCONFIG SYS"
kernel_name: kernel_name:
db "RDOS SYS" db "RDOS SYS"

View File

@ -1,35 +0,0 @@
; Reads a single character with echo
; out AL character
isr_getc_echo:
xor ax, ax
int 0x16
test al, al
jz isr_getc_echo
call putc
iret
; Reads a single character without echo
; out AL character
isr_getc:
xor ax, ax
int 0x16
test al, al
jz isr_getc
iret
; Prints a single character
; in DL character
isr_putc:
push ax
mov al, dl
call putc
pop ax
iret
putc:
push bx
mov ah, 0x0e
mov bx, 0x0000
int 0x10
pop bx
ret

View File

@ -1,53 +0,0 @@
; drive table
%define drivetab_type 0x00 ; BYTE 0=unassigned, 1=BIOS/CHS, 2=BIOS/LBA
%define drivetab_num 0x01 ; BYTE DL number
; CHS data for type=1
; Might be reused for driver address
%define drivetab_heads 0x02 ; WORD CHS heads
%define drivetab_spt 0x04 ; WORD CHS sectors per track
%define drivetab_sectors 0x06 ; DWORD total number of sectors
%define drivetab_offset 0x0A ; DWORD partition offset
%define drivetab_size 0x0E
drive_table:
dw 0
.count:
dw 4
; DI is incremented for the space taken
; IN ES:DI
drive_setup:
xor cx, cx
mov [drive_table], di
mov al, drivetab_size
mov ah, BYTE [drive_table.count]
mul ah
xchg cx, ax
; this increments DI and also fills table with zeros
rep stosb
ret
; Load a drive table entry
; IN DL drive number
; OUT DS:SI ptr to table item
drive_load:
; bail out if number too high
cmp dl, [cs:drive_table.count]
jnc .err
push cs
pop ds
mov si, [drive_table]
push ax
mov al, drivetab_size
mul dl
add si, ax
pop ax
ret
.err:
stc
ret

View File

@ -1,30 +0,0 @@
; Register a interrupt handler (21h AH=25h)
; in: AL interrupt number
; DS:DX far ptr
isr_intr_register:
; backup previous stos ptr
push es
push di
; DI = AL * 4
mov ah, 4
mul ah
mov di, ax
; ES = 0
xor ax, ax
mov es, ax
; store offset
mov ax, dx
stosw
; store segment
mov ax, ds
stosw
; restore previous stos ptr
pop di
pop es
iret

View File

@ -1,64 +1,57 @@
cpu 8086 cpu 8086
org 0x0
; Memory layout (starting from top)
%define self 0xF000
%define diskbuf (self-0x200)
%define stack (diskbuf) ; end addr, grows down
org self
jmp init jmp init
isr_dos_main: banner:
cmp ah, 0x01 db "RDOS 2019-09", 0x0A, 0x0D, 0
je isr_getc_echo
cmp ah, 0x02
je isr_putc
cmp ah, 0x25
je isr_intr_register
jmp isr_invalid
%include "intr.asm" print_banner:
%include "chario.asm" mov cl, 2
mov si, banner
; ISR for invalid subfunctions or unimplemented .loop:
isr_invalid: mov dl, BYTE [si]
mov bp, 0xFEFE test dl, dl
int3 jz .end
.hlt: call cpm_syscall
hlt inc si
jmp .hlt jmp .loop
; ISR tail to set carry flag to signal error .end:
isr_error: ret
push bp
mov bp, sp
; set carry flag
or WORD [SS:BP+6], 1
pop bp
isr_return:
iret
%include "drive.asm"
init: init:
mov ax, cs mov sp, stack
mov ds, ax
mov es, ax
call config_first_run call print_banner
int3
mov di, kernel_end
call drive_setup
mov dx, isr_dos_main
mov ax, 0x2521
pushf
push cs
call isr_dos_main
mov dl, 0x37
mov ah, 0x02
int 0x21
cli cli
.halt: .halt:
hlt hlt
jmp .halt jmp .halt
cpm_syscall:
cmp cl, 0x02
je putc
stc
ret
putc:
push ax
push bx
mov al, dl
mov ah, 0x0e
mov bx, 0x0000
int 0x10
pop bx
pop ax
ret
%include "string.asm" %include "string.asm"
%include "config.asm"
kernel_end: kernel_end: