summaryrefslogtreecommitdiff
path: root/boot.asm
diff options
context:
space:
mode:
authorJoseph Hunkeler <jhunkeler@gmail.com>2017-11-28 16:49:24 -0500
committerJoseph Hunkeler <jhunkeler@gmail.com>2017-11-28 16:49:24 -0500
commit1dd05ebe61c95985b16d170bf2d3f081a02dfd7d (patch)
tree216d65aa993cba84c1b58e7152efd516b37121cc /boot.asm
downloadminos-1dd05ebe61c95985b16d170bf2d3f081a02dfd7d.tar.gz
Initial commit
Diffstat (limited to 'boot.asm')
-rw-r--r--boot.asm246
1 files changed, 246 insertions, 0 deletions
diff --git a/boot.asm b/boot.asm
new file mode 100644
index 0000000..d6ddfa1
--- /dev/null
+++ b/boot.asm
@@ -0,0 +1,246 @@
+bits 16
+
+jmp start
+
+CR equ 0Dh
+LF equ 0Ah
+K_CS_ADDR equ 007eh
+
+start:
+ mov ax, 07c0h
+ mov ds, ax ; set data segment
+ mov ax, 07e0h
+ mov ss, ax ; set stack segment
+ mov sp, 2000h ; 8192k
+
+ push bp ; set up stack frame
+ mov bp, sp
+ sub sp, 2 ; local storage
+
+ mov [drive0], dl ; save first detected drive
+
+ call cls ; clear screen
+
+ push 0 ;
+ call setcursor ; set cursor position
+
+ push banner ;
+ call puts ; print version
+ add sp, 2 ; clean up
+
+ push word [drive0]
+ call disk_reset
+ add sp, 2
+
+ xor cx, cx
+ mov ax, K_CS_ADDR
+ mov es, ax
+
+ push msg_loading
+ call puts
+ add sp, 2
+
+ mov bx, 0
+ mov di, 2 ; start at sector
+.loader:
+ mov al, 1 ; read one sector
+ mov cx, di ; track/cyl | sector number
+ mov dh, 0 ; head number
+ mov dl, [drive0] ; drive number
+ call disk_read
+
+ push '.'
+ call putc
+ add sp, 2
+
+ add bx, 200h ; increment address by 512 bytes
+ inc di ; increment sector read count
+ cmp di, 16 ; 8K (i'll make this smarter later)
+ jle .loader ; keep reading
+
+ push msg_done
+ call puts
+ add sp, 2
+
+ add sp, 2 ; remove local storage
+ mov sp, bp
+ pop bp
+
+ mov dx, [drive0] ; the kernel will need the boot drive number
+ jmp K_CS_ADDR:0000h ; jump to kernel address
+
+ cli ; disable interrupts
+ jmp $ ; hang
+
+panic:
+ ; Hang system with supplied error message
+ push bp
+ mov bp, sp
+
+ push error_msg_panic ; i.e. 'PANIC:'
+ call puts
+ add sp, 2
+
+ push word [bp + 4] ; address of error string buffer
+ call puts ; print error
+ add sp, 2
+
+ cli ; disable interrupts
+ jmp $ ; hang (no return)
+ ; stack is dead
+
+
+disk_reset:
+ push bp
+ mov bp, sp
+ pusha
+
+ mov ah, 00h ; reset disk
+ mov dl, [bp + 4] ; disk number
+ int 13h ; BIOS disk service
+ jnc .success
+
+ push error_msg_disk_reset
+ call panic
+
+.success:
+ popa
+ mov sp, bp
+ pop bp
+ ret
+
+
+disk_read:
+ push bp
+ mov bp, sp
+
+ push di
+ mov di, 3 ; retry counter
+.readloop:
+ push ax
+ push bx
+ push cx
+
+ mov ah, 02h ; BIOS - read disk sectors
+ int 13h ; BIOS disk service
+
+ jnc .success
+
+ push dx
+ call disk_reset
+ add sp, 2
+
+ pop cx
+ pop bx
+ pop ax
+
+ dec di
+ jnz .readloop
+
+ push error_msg_disk_read
+ call panic
+ add sp, 2
+
+.success:
+ pop di
+ mov sp, bp
+ pop bp
+ ret
+
+
+cls:
+ push bp
+ mov bp, sp
+ pusha
+
+ mov ah, 07h ; BIOS - scroll down
+ mov al, 00h ; lines to scroll (0 == entire screen)
+ mov bx, 0700h ; color white/black
+ ; & video page zero
+ mov cx, 0
+ mov dh, 24 ; rows
+ mov dl, 79 ; cols
+ int 10h ; BIOS video service
+ popa
+
+ mov sp, bp
+ pop bp
+ ret
+
+
+setcursor:
+ push bp
+ mov bp, sp
+ pusha
+
+ mov ah, 02h ; BIOS - set cursor position
+ mov bh, 0 ; video page zero
+ mov dx, [bp + 4] ; address of new cursor value
+ int 10h ; BIOS video service
+
+ popa
+ mov sp, bp
+ pop bp
+ ret
+
+
+putc:
+ ; Write single character at cursor position
+ push bp
+ mov bp, sp
+ pusha
+
+ mov ah, 0eh ; BIOS - teletype
+ mov al, [bp + 4] ; character
+ mov bx, 0 ; video page zero
+ int 10h ; BIOS video service
+
+ popa
+ mov sp, bp
+ pop bp
+ ret
+
+
+puts:
+ ; Write string buffer at cursor position
+ push bp
+ mov bp, sp
+ pusha
+
+ mov si, [bp + 4] ; address of string buffer
+ mov bx, 0000h ;
+ mov ah, 0eh ; BIOS - teletype
+
+.loop:
+ lodsb ; load byte at [si] into al
+ or al, 0 ; 0 | 0 = 0 (detect null terminator)
+ je .end
+ int 10h ; BIOS video service
+ jmp .loop
+.end:
+ popa
+ mov sp, bp
+ pop bp
+ ret
+
+
+
+; data
+drive0: dw 0
+banner: db "MINOS Bootloader", CR, LF, 0
+
+; General messages
+msg_loading: db "Loading", 0
+msg_done: db "done!", CR, LF, 0
+msg_disk_reset: db "Drive reset successful.", CR, LF, 0
+msg_disk_read: db "Sector read successful.", CR, LF, 0
+
+; Error messages
+error_msg_panic: db "PANIC: ", 0
+error_msg_disk_reset: db "Drive reset failed!", CR, LF, 0
+error_msg_disk_read: db "Drive read failed!", CR, LF, 0
+
+; boot signature
+times 510-($-$$) db 0
+dw 0xAA55
+