Previous lesson Table of Contents Next lesson]
All of this printing stuff to the screen is fun, but no operating system would be any good at all if it did not provide any interactivity. Let’s make it read input from the keyboard. Again we will be using calls to a function in BIOS to read the keyboard.
We are going to be using function 0, interrupt 0x16. This is done easily with the following two instructions.
xor ah, ah ; we want function zero int 0x16 ; wait for a keypress
This function causes the computer to pause and does not return until a key is pressed. This can be used in a “Press any key to continue” situation, or also if you want to get input from the user. The scan code of the key pressed will be returned in register AH, and the ASCII code is returned in AL.
Your assignment for this lesson is to write a simple boot program that demonstrates a bit of interactivity. Perhaps it could print a message each time a key is pressed. Or maybe allow the user to type at the keyboard and echo each character to the screen as it is typed.
If you get stuck, below is an example of my own. But it's no fair peeking until you’ve tried by yourself!
In the next lesson we will learn how to make our operating system larger than the single sector of the Boot Record.
;----------------------------------------------------------------------
; Interactivity Example Boot Program
;
; Joel Gompert 2001
;
; Disclaimer: I am not responsible for any results of the use of the contents
; of this file
;----------------------------------------------------------------------
org 0x7c00 ; This is where BIOS loads the bootloader
; Execution begins here
entry:
jmp short begin ; jump over the DOS boot record data
; ----------------------------------------------------------------------
; data portion of the "DOS BOOT RECORD"
; ----------------------------------------------------------------------
brINT13Flag DB 90H ; 0002h - 0EH for INT13 AH=42 READ
brOEM DB 'MSDOS5.0' ; 0003h - OEM name & DOS version (8 chars)
brBPS DW 512 ; 000Bh - Bytes/sector
brSPC DB 1 ; 000Dh - Sectors/cluster
brResCount DW 1 ; 000Eh - Reserved (boot) sectors
brFATs DB 2 ; 0010h - FAT copies
brRootEntries DW 0E0H ; 0011h - Root directory entries
brSectorCount DW 2880 ; 0013h - Sectors in volume, < 32MB
brMedia DB 240 ; 0015h - Media descriptor
brSPF DW 9 ; 0016h - Sectors per FAT
brSPH DW 18 ; 0018h - Sectors per track
brHPC DW 2 ; 001Ah - Number of Heads
brHidden DD 0 ; 001Ch - Hidden sectors
brSectors DD 0 ; 0020h - Total number of sectors
DB 0 ; 0024h - Physical drive no.
DB 0 ; 0025h - Reserved (FAT32)
DB 29H ; 0026h - Extended boot record sig
brSerialNum DD 404418EAH ; 0027h - Volume serial number (random)
brLabel DB 'Joels disk ' ; 002Bh - Volume label (11 chars)
brFSID DB 'FAT12 ' ; 0036h - File System ID (8 chars)
;------------------------------------------------------------------------
; --------------------------------------------
; Boot program code begins here
; --------------------------------------------
; boot code begins at 0x003E
begin:
xor ax, ax ; zero out ax
mov ds, ax ; set data segment to base of RAM
mov si, msg ; load address of our message
call putstr ; print the message
loop1:
xor ah, ah ; function 0
int 0x16 ; get a key from the keyboard
mov si, charmsg ; load address of message
call putstr ; print the message
mov ah, 0x0e ; function print character
mov bl, 0x07 ; white on black
int 0x10
mov si, newline ; print a newline
call putstr
jmp loop1 ; just loop forever.
; --------------------------------------------
; data for our program
msg db 'Press a key.'
newline db 13,10,0
charmsg db 'Character: ',0
; ---------------------------------------------
; Print a null-terminated string on the screen
; ---------------------------------------------
putstr:
push ax
putstrl:
lodsb ; AL = [DS:SI]
or al, al ; Set zero flag if al=0
jz putstrd ; jump to putstrd if zero flag is set
mov ah, 0x0e ; video function 0Eh (print char)
mov bx, 0x0007 ; color
int 0x10
jmp putstrl
putstrd:
pop ax
retn
;---------------------------------------------
size equ $ - entry
%if size+2 > 512
%error "code is too large for boot sector"
%endif
times (512 - size - 2) db 0
db 0x55, 0xAA ;2 byte boot signature
No comments:
Post a Comment