summaryrefslogtreecommitdiff
path: root/boot/bios.inc
diff options
context:
space:
mode:
authorAiden Gall <aiden@aidengall.xyz>2024-05-14 19:43:28 +0100
committerAiden Gall <aiden@aidengall.xyz>2024-05-14 19:51:05 +0100
commit93585dc4da3be099e1ffe7e757aa7caff2e1f013 (patch)
treec1335acdd74cff12e545ce386ab2dbd176eaa473 /boot/bios.inc
initial commit
Diffstat (limited to 'boot/bios.inc')
-rw-r--r--boot/bios.inc128
1 files changed, 128 insertions, 0 deletions
diff --git a/boot/bios.inc b/boot/bios.inc
new file mode 100644
index 0000000..ccc94e3
--- /dev/null
+++ b/boot/bios.inc
@@ -0,0 +1,128 @@
+macro bios_a20_enable {
+ mov ax, 0x2401
+ int 0x15
+}
+
+macro bios_vga_write_mode_3 {
+ mov ax, 0x03
+ int 0x10
+}
+
+; assumes dl = drive number
+macro bios_disk_read dst*, cyl*, head*, sector*, count*, err_label* {
+ local read_disk
+
+ assert 0 <= cyl & cyl <= 1023
+ assert 0 <= head & head <= 15
+ assert 1 <= sector & sector <= 17
+ assert 1 <= count & count <= 128
+
+ ; try to read disk up to 3 times
+ mov di, 3
+
+read_disk:
+ ; ah = 0x02, al = number of sectors to read
+ mov ax, (0x0200 or count)
+
+ ; es:bx = pointer to destination buffer
+ if dst = 0
+ xor bx, bx
+ else
+ mov bx, dst
+ end if
+
+ ; ch = track/cylinder number, cl = sector number
+ mov cx, ((cyl and 0xff) shl 8) or ((cyl and 0x300) shl 6) or sector
+
+ ; dh = head number
+ if head = 0
+ xor dh, dh
+ else
+ mov dh, head
+ end if
+
+ int 0x13
+
+ jc .error
+ cmp ax, count
+ jne .error
+
+ jmp .exit
+.error:
+ dec di
+ jz err_label
+
+ ; reset disk on error
+ xor ah, ah
+ stc
+ int 0x13
+ jc err_label
+ jmp read_disk
+.exit:
+}
+
+macro bios_e820_mmap mmap*, err_label* {
+ local e820, e820_entry
+e820:
+ virtual at di
+ label e820_entry
+ .base dq ?
+ .length dq ?
+ .type dd ?
+ .ext_attr dd ?
+ .sizeof = $ - e820_entry
+ end virtual
+
+ mov di, mmap + 4
+ xor ebx, ebx
+ xor bp, bp
+
+ mov edx, 0x0534d4150
+ mov eax, 0xe820
+ mov byte [.ext_attr], 0x01
+ mov ecx, .sizeof
+ int 0x15
+ jc err_label
+
+ mov edx, 0x0534d4150
+ cmp eax, edx
+ jne err_label
+
+ test ebx, ebx
+ jz err_label
+
+ jmp @f
+
+.e820_loop:
+ mov ax, 0xe820
+ mov byte [.ext_attr], 0x01
+ mov ecx, .sizeof
+ int 0x15
+ jc err_label
+
+ mov edx, 0x0534d4150
+@@:
+ jcxz .skip_entry
+
+ ; ACPI < 3.0
+ cmp cl, (.sizeof-4)
+ jbe .not_ext
+
+ ; ignore data flag
+ test byte [.ext_attr], 0x01
+ jz .skip_entry
+
+.not_ext:
+ mov ecx, dword [.length]
+ or ecx, dword [.length + 4]
+ jz .skip_entry
+
+ inc bp
+ add di, .sizeof
+.skip_entry:
+ test ebx, ebx
+ jnz .e820_loop
+
+ ; store e820 mmap entry count at beginning
+ mov [mmap], bp
+}