; Spanning whole conventional memory ; Sector size 0x200 (512 bytes) ; Start address 0x00600, 3 hidden sectors for IVT and BDA ; Kernel .data may be in reserved sectors ; Ramdisk I/O, similar invocation to BIOS int 13h ; in AH 42=read, 43=write ; in DS:SI location of disk address packet ; out AH error code or 00 (also in CF) ramdisk_io: ; backup original values push cx push dx push si push di push ds push es ; 3 most significant addr bytes must be all zero test WORD [ds:si+0x0E], 0xFFFF jnz .invaddr test WORD [ds:si+0x0C], 0xFFFF jnz .invaddr test WORD [ds:si+0x0A], 0xFFFF jnz .invaddr ; calculate segment register for ramdisk access mov dx, [ds:si+0x08] cmp dx, 0x07fd ; 0x800 sectors in adress space, 3 hidden jge .invaddr mov cl, 0x05 ; 2^5 = 32 paragraphs per sector sal dx, cl add dx, 0x0060 ; 3 hidden sectors xor cx, cx push cx ; offset = 0 push dx ; segment ; store addresses for buffer access mov dx, [ds:si+0x04] push dx ; offset mov dx, [ds:si+0x06] push dx ; segment ; setup transfer length (in words) in CX mov dx, [ds:si+0x02] ; sector count mov cx, 0x0008 ; 2^8 = 256 words per sector sal dx, cl xchg dx, cx cmp ah, 0x42 je .read cmp ah, 0x43 je .write sub sp, 8 ; remove src & dst pointers from stack .invval: mov ah, 0x01 stc jmp .ret .invaddr: ; out of bounds mov ah, 0x04 stc jmp .ret .read: pop es ; ES:DI buffer pop di pop ds ; DS:SI ramdisk data pop si rep movsw clc jmp .ret .write: pop ds ; DS:SI buffer pop si pop es ; ES:DI ramdisk data pop di rep movsw clc .ret: ; restore backupped values pop es pop ds pop di pop si pop dx pop cx ret