idk what i added
This commit is contained in:
@@ -14,7 +14,7 @@ disk_load_root:
|
||||
pusha
|
||||
mov ax, 19 ; First sector of root entry
|
||||
call math_lba_to_chs ; Assigns ch, cl and dh the correct values
|
||||
xor ax,ax
|
||||
xor ax,ax ; clear ax so I can use it on next line
|
||||
mov dl, [ebr_drive_number] ; Drive number
|
||||
mov ah, 02h ; BIOS ah code for read disk sectors to memory
|
||||
mov al, 0Ch ; Root directory has 12 sectors
|
||||
@@ -53,28 +53,34 @@ disk_load_root:
|
||||
; ---------------------------------------------
|
||||
|
||||
; Reads a certain number of sectors into memory
|
||||
; int 13h/ah = 02h read disk sectors into memory
|
||||
; IN
|
||||
; ax = LBA
|
||||
; es:bx = area to read to/write from
|
||||
; [read_write_flag] = 02 or 03 for read or write
|
||||
; dl = ebr drive number
|
||||
; int 13h/ah = 02h/03h read/write disk sectors into memory
|
||||
; al = number of sectors to read
|
||||
; ah = read/write 02=read, 03=write IMPORTANT
|
||||
; ch = cylinder number
|
||||
; cl = sector number
|
||||
; dh = head number
|
||||
; dl = drive number
|
||||
; es:bx = points to data buffer
|
||||
disk_read:
|
||||
disk_read_or_write:
|
||||
push ax
|
||||
push bx
|
||||
push cx
|
||||
push dx
|
||||
push di
|
||||
|
||||
|
||||
; cl = sector
|
||||
; ch = cylinder
|
||||
; dh = head
|
||||
; dl = drive
|
||||
call math_lba_to_chs ; Get the chs address
|
||||
|
||||
mov ah, 02h ; BIOS ah code for read disk sectors to memory
|
||||
mov ah, [read_write_flag]
|
||||
mov al, 1
|
||||
|
||||
; repeat drive read 3 times (incase of random error)
|
||||
mov di, 3 ; counter
|
||||
@@ -122,10 +128,55 @@ disk_read:
|
||||
pop ax
|
||||
ret
|
||||
|
||||
; -------------------------------------
|
||||
|
||||
; -------------------------------------
|
||||
; CLEAR DATA
|
||||
; Uses the metadata buffer to determine the file size in the data buffer and clears it.
|
||||
disk_clear_file_buffer:
|
||||
pusha
|
||||
|
||||
mov si, metadata_buffer
|
||||
mov cx, [si+28] ; MOve the filelength into the ax
|
||||
shr cx, 1 ; Divide by 4 because we'll write over using double words
|
||||
mov si, empty_word
|
||||
lodsb ; Load the empty dword
|
||||
mov di, file_buffer
|
||||
.loop:
|
||||
stosb
|
||||
dec cx
|
||||
cmp cx, 0
|
||||
jbe .loop
|
||||
.finish:
|
||||
popa
|
||||
ret
|
||||
disk_clear_output_buffer:
|
||||
pusha
|
||||
mov cx, 0x7f0 ; Length of the output buffer
|
||||
mov si, empty_word
|
||||
lodsb ; Load the empty word into ax
|
||||
mov di, output_buffer
|
||||
.loop:
|
||||
stosb ; Store empty dword in di
|
||||
dec cx
|
||||
cmp cx, 0
|
||||
ja .loop
|
||||
.finish:
|
||||
popa
|
||||
ret
|
||||
|
||||
; -------------------------------------
|
||||
; IN
|
||||
; si: filename
|
||||
|
||||
; OUT
|
||||
; data_buffer: file contents
|
||||
; TODO use predefined data for calculations
|
||||
disk_load_file:
|
||||
pusha
|
||||
call os_string_length ; cl = string length
|
||||
cmp cl, 11
|
||||
ja .filename_too_long
|
||||
|
||||
mov di, fat12_file_name
|
||||
call os_format_fat_filename
|
||||
|
||||
@@ -134,7 +185,7 @@ disk_load_file:
|
||||
xor bx,bx
|
||||
.search_root:
|
||||
mov di, fat12_file_name ; Move the name of the kernel into di
|
||||
mov cx, 11 ; length of 'KERNEL BIN'
|
||||
mov cx, 11 ; length of filenames in fat12
|
||||
push si ; Preserve si
|
||||
repe cmpsb ; Repeat a comparison of bytes between file name and current bytes until it finds a match
|
||||
pop si ; Retrieve si
|
||||
@@ -147,29 +198,179 @@ disk_load_file:
|
||||
|
||||
jmp .file_not_found ; If the last dir has been searched, then there is no kernel
|
||||
.found_file:
|
||||
call disk_clear_file_buffer
|
||||
mov di, metadata_buffer
|
||||
mov cx, 32
|
||||
.write_metadata:
|
||||
; Write data to metadata buffer
|
||||
lodsb
|
||||
stosb
|
||||
sub cx, 1
|
||||
cmp cx, 0
|
||||
jne .write_metadata
|
||||
.read_kernel:
|
||||
sub si, 32
|
||||
mov ax, [si+28] ; File length
|
||||
mov [file_length], ax
|
||||
mov ax, [si+26] ; ax is now a pointer to the pointer to the file relative to the data segments :D
|
||||
add ax, 20h
|
||||
add ax, 1Fh
|
||||
mov [file_cluster], ax
|
||||
; Setup registers for disk read
|
||||
mov bx, data_buffer
|
||||
mov si, file_buffer
|
||||
mov bx, si
|
||||
mov dl, [ebr_drive_number]
|
||||
|
||||
call disk_read ; Load file from disk into memory
|
||||
mov ch, 02h
|
||||
mov [read_write_flag], ch ; READ
|
||||
call disk_read_or_write ; Load file from disk into memory
|
||||
jmp .done
|
||||
.file_not_found:
|
||||
mov si, file_not_found
|
||||
call os_print_string
|
||||
jmp .done
|
||||
.filename_too_long:
|
||||
mov si, too_long_filename
|
||||
call os_print_string
|
||||
jmp .done
|
||||
.done:
|
||||
popa
|
||||
ret
|
||||
|
||||
; Write data to file
|
||||
; takes the contents in the data buffer for a fixed
|
||||
; number of characters definied by [file_length]
|
||||
; and write it to the file that si points to
|
||||
; It also must edit the fat entry data
|
||||
disk_write_file:
|
||||
pusha
|
||||
; Check if file name is too long
|
||||
call os_string_length ; cl = string length
|
||||
cmp cl, 11
|
||||
ja .filename_too_long
|
||||
; Convert file name to a fat filename
|
||||
mov di, fat12_file_name
|
||||
call os_format_fat_filename
|
||||
|
||||
; Locate the file entry in memory
|
||||
; Prepare values
|
||||
mov si, root_buffer
|
||||
xor bx,bx
|
||||
.search_root:
|
||||
mov di, fat12_file_name ; Move the name of the kernel into di
|
||||
mov cx, 11 ; length of filenames in fat12
|
||||
push si ; Preserve si
|
||||
repe cmpsb ; Repeat a comparison of bytes between file name and current bytes until it finds a match
|
||||
pop si ; Retrieve si
|
||||
je .found_file
|
||||
|
||||
section .data:
|
||||
disk_read_fail: db 'Error: Could not read disk\n', 0
|
||||
file_not_found: db 'File not found\n', 0
|
||||
file_found: db 'File found\n', 0
|
||||
loading_root: db 'Loading root diretory\n', 0
|
||||
file_cluster: dw 0
|
||||
fat12_file_name: db ' '
|
||||
add si, 32 ; increment di to the next directory entry
|
||||
inc bx
|
||||
cmp bx, [bdb_dir_entries_count] ; Have we reached the number of directories that exist
|
||||
jl .search_root ; Repeat search
|
||||
|
||||
jmp .file_not_found ; If the last dir has been searched, then there is no kernel
|
||||
.found_file:
|
||||
; Find where the file is on the disk
|
||||
mov ax, [si+28] ; File length entry
|
||||
mov [file_length], ax
|
||||
mov ax, [si+26] ; ax is now a pointer to the pointer to the file relative to the data segments :D
|
||||
add ax, 1Fh
|
||||
mov [file_cluster], ax
|
||||
; Setup registers for disk read
|
||||
mov si, file_buffer
|
||||
mov bx, si
|
||||
mov dl, [ebr_drive_number]
|
||||
|
||||
mov ch, 03h
|
||||
mov [read_write_flag], ch ; WRITE
|
||||
call disk_read_or_write ; Load file from disk into memory
|
||||
jmp .finish
|
||||
; DI now points to a fat12 formatted file name
|
||||
|
||||
; Write to those sectors
|
||||
; Update FAT entry
|
||||
.file_not_found: ; TODO create a file if it's not found
|
||||
mov si, file_not_found
|
||||
call os_print_string
|
||||
jmp .finish
|
||||
.filename_too_long:
|
||||
mov si, too_long_filename
|
||||
call os_print_string
|
||||
jmp .finish
|
||||
.finish:
|
||||
popa
|
||||
ret
|
||||
|
||||
; TODO support long file names
|
||||
; Store a list of the files in file_buffer
|
||||
; in a human readable format
|
||||
; OUT
|
||||
; output_buffer: the list (string)
|
||||
disk_list_contents:
|
||||
pusha
|
||||
mov si, root_buffer
|
||||
mov di, output_buffer
|
||||
.loop:
|
||||
call string_unformat_fat_filename
|
||||
mov cx, 000Ch
|
||||
sub cx, [file_name_length]
|
||||
add di, [file_name_length]
|
||||
mov al, 20h
|
||||
.space_loop:
|
||||
stosb
|
||||
dec cx
|
||||
cmp cx, 0
|
||||
jne .space_loop
|
||||
|
||||
.file_attribute:
|
||||
add si, 11d
|
||||
lodsb
|
||||
push si
|
||||
|
||||
mov si, read_only
|
||||
cmp al, 1h
|
||||
je .add_string
|
||||
mov si, hidden
|
||||
cmp al, 2h
|
||||
je .add_string
|
||||
mov si, system
|
||||
cmp al, 4h
|
||||
je .add_string
|
||||
mov si, volume
|
||||
cmp al, 8h
|
||||
je .add_string
|
||||
mov si, directory
|
||||
cmp al, 10h
|
||||
je .add_string
|
||||
mov si, archive
|
||||
cmp al, 20h
|
||||
je .add_string
|
||||
|
||||
.after_file_attributes:
|
||||
pop si
|
||||
|
||||
mov al, 0Ah
|
||||
stosb
|
||||
|
||||
add si, 20d
|
||||
lodsb ; +1
|
||||
dec si ; -1
|
||||
cmp al, 0 ; You've come to the end of the root entries
|
||||
je .finish
|
||||
cmp al, 00E5h ; E5h is a marker that the Fat entry is available
|
||||
je .finish
|
||||
jmp .loop
|
||||
.add_string:
|
||||
.add_string_loop:
|
||||
lodsb
|
||||
cmp ax, 00h
|
||||
je .after_file_attributes
|
||||
stosb
|
||||
jmp .add_string_loop
|
||||
.finish:
|
||||
mov cx, output_buffer
|
||||
sub di, cx
|
||||
mov [file_length], di
|
||||
stosb
|
||||
popa
|
||||
ret
|
||||
|
||||
Reference in New Issue
Block a user