;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;; Miguel's FoolOS Helper Functions ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; ;disk_load_16 ; [bits 16] DISK_LOAD: db "D",0 DISK_LOAD_ERROR db "E",0 Head: db 0 Track: db 0 Sector: db 1 LBA: dw 0 ;; starts at zero! Sectors: dw 80 Heads: dw 2 ;disk_load routune (load dh sectors from drive dl to es:bx) ;lba mode has 52 sectors hardcoded! disk_load_16: pusha ;;; ; check if LBA is supported ;;; pusha ;;; mov ah,0x41 ;;; mov bx,0x55aa ;;; int 0x13 ;;; jnc disk_load_lba ;;; popa disk_load_next: call ESBX ; load using CHS ;; mov al,80 ;read dh sectors (amount) ;; mov cx,[LBA] ;; cmp cx,0 ;; jne disk_read_normal ;; mov al,79 ;read dh sectors (amount) ;; disk_read_normal mov al,1 mov cl,[Sector] ;sector mov ch,[Track] ;cyl mov dl,[BOOT_DRIVE] mov dh,[Head] ;head mov ah,0x02 ;BIOS read sector func int 0x13 ;bios interrupt jnc disk_read_ok ;ready becaue of error :( mov bx, DISK_LOAD_ERROR call print_string jmp $ disk_read_ok: mov ax,[LBA] cmp ax,880 je disk_load_ready mov bx, DISK_LOAD call print_string add ax,1 ;conver LBA to CHS mov [LBA],ax call LBACHS jmp disk_load_next disk_load_ready: jmp $ popa ret ESBX: xor dx,dx xor dx,dx mov ax,[LBA] mov bx,0x200 mul bx mov bx,ax add dx,1 shl dx,12 mov es,dx ret ; load using LBA ;;;disk_load_lba: ;;; ;;; popa ;;; ;;; xor ah,ah ;;; mov ah,0x42 ;;; lea si,[lba_adr] ;;; int 0x13 ;;; jc skip_print ;;; mov bx, DISK_LOAD ;;; call print_string ;;; skip_print: ;;; ;;; popa ;;; ret ;;; LBACHS: xor dx, dx ; prepare dx:ax for operation div WORD [Sectors] ; divide by sectors per track inc dl ; add 1 (obsolute sector formula) mov BYTE [Sector], dl xor dx, dx ; prepare dx:ax for operation div WORD [Heads] ; mod by number of heads (Absolue head formula) mov BYTE [Head], dl ; everything else was already done from the first formula mov BYTE [Track], al ; not much else to do :) ret lba_adr: dw 0x10 ; size of packet ( 16 byte) dw 53 ; number of sectors to read dw 0x0000 ; target addr. offset dw 0x1000 ; target addr. sector dd 1 ; first sector to read dd 0 ;