summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/boot/bootloader.asm70
1 files changed, 67 insertions, 3 deletions
diff --git a/src/boot/bootloader.asm b/src/boot/bootloader.asm
index eb226a6..4b803fa 100644
--- a/src/boot/bootloader.asm
+++ b/src/boot/bootloader.asm
@@ -36,15 +36,13 @@ step2:
or eax, 0x1
mov cr0, eax
- jmp $
-; jmp CODE_SEG:start_32
+ jmp CODE_SEG:start_32
; GDT table description
gdt_start:
gdt_null: ; First segment Descriptor is always 0
dd 0x0
dd 0x0
-
;Second segment descriptor... Code segment - 0x8
gdt_code:
dw 0xffff ; Segment limit 0-15
@@ -74,6 +72,72 @@ gdt_table:
dw gdt_end - gdt_start - 1
dd gdt_start
+[BITS 32]
+start_32:
+ mov eax, 1 ; LBA addr to start from
+ mov ecx, 100 ; Num of sectors
+ mov edi, 0x00100000 ; Mem addr to load data read
+ call ata_lba_read
+ jmp CODE_SEG:0x0100000
+
+ata_lba_read:
+ ; Write the high 8bits of the LBA to the disk controller
+ mov ebx, eax,
+ shr eax, 24 ; Get LBA high 8bits to send to the controller
+ or eax, 0xE0 ; Select the 'master' drive
+ mov dx, 0x1F6 ; Port number
+ out dx, al ; Write bits to the port
+
+ ; Write the number of sectors to read to the disk controller
+ mov eax, ecx ; Num of sectors
+ mov dx, 0x1F2 ; Port number
+ out dx, al ; Send to the port
+
+ ; Send LBA's first 0-7 bits
+ mov eax, ebx ; Get original LBA
+ mov dx, 0x1F3 ; Port number
+ out dx, al ; Write the low 8 bits to the controller
+
+ ; Send LBA's bits 8-15 to the controller
+ mov eax, ebx ; Get original LBA
+ mov dx, 0x1F4 ; Port number
+ shr eax, 8 ; Get bits 8-15
+ out dx, al ; Write 8 bits to controller
+
+ ; Send LBA's bits 16-23 to the controller
+ mov eax, ebx ; Get original LBA
+ mov dx, 0x1F5 ; Port number
+ shr eax, 16 ; Get bits 16-23
+ out dx, al ; Write to the controller
+
+ ; No idea what it does yet
+ mov dx, 0x1F7
+ mov al, 0x20
+ out dx, al
+
+ ; Read sectors into memory
+.next_sector:
+ push ecx ; Save num of sectors
+
+ ; Loop here until the controller is ready
+.try_again:
+ mov dx, 0x1f7
+ in al, dx
+ test al, 8
+ jz .try_again
+
+ mov ecx, 256
+ mov dx, 0x1F0
+ rep insw ; Read 256 words from the I/O port in DX into memory ES:EDI
+ ; EDI has been set to 0x100000 above
+ ; ecx controls how many words to read (w means word in ins)
+ ; 256 * 2 bytes-per-word - We read a whole sector
+
+ pop ecx ; restor num of sectors
+ loop .next_sector ; This decrements ecx too
+
+ ret
+
; Fill in to the end and add bootloader signature
times 510 - ($ - $$) db 0
dw 0xAA55