I just finished writing my 16 bit operating system but I used int 0x16 to tell which key the user pressed. Now I want to write my own keyboard driver and I don't want to use any interrupts. (So that I can enter long mode). I realized there are two scan codes, the AT and the XT.
How can I determine which keyboard does the computer use in NASM x86 assembly?
Should I ask the user to press a key and determine using the scan code in port 0x60 when the OS boots?
eg: A key - 0x1c(make) for AT and 0x1e(make) for XT
But linux does not do that.......
I used the following code and discovered virtual box uses an XT keyboard....
[org 0x2e00]
mov bx, 0x1000
mov ds, bx ;The program is loaded at 0x12e00 or 1000:2e00 by the operating system
xor ax, ax ;Set AX to zero
mov bl, 0x0e ;Set text color
loop: ;Main loop
in al, 0x60 ;Read all ports and display them
mov cx, ax
call hex_print ;Print content of the port in hex
in al, 0x61
mov cx, ax
call hex_print
in al, 0x62
mov cx, ax
call hex_print
in al, 0x63
mov cx, ax
call hex_print
in al, 0x64
call hex_print
call com_cls ;Clear the screen after printing content
jmp loop ;Jump to loop
;Print hex values;;;;;;;;;;;;;;;;;
hex_print:
push ax
push cx
mov ah, 0x0e
mov al, ' '
int 0x10
mov al, '0'
int 0x10
mov al, 'x'
int 0x10
hex_print_start:
mov al, ch
and al, 0xf0
call hex_map
int 0x10
shl cx, 0x04
mov al, ch
and al, 0xf0
call hex_map
int 0x10
shl cx, 0x04
mov al, ch
and al, 0xf0
call hex_map
int 0x10
shl cx, 0x04
mov al, ch
and al, 0xf0
call hex_map
int 0x10
hex_print_end:
pop cx
pop ax
ret
hex_map:
cmp al, 0x00
jne zero_end
mov al, '0'
ret
zero_end:
cmp al, 0x10
jne one_end
mov al, '1'
ret
one_end:
cmp al, 0x20
jne two_end
mov al, '2'
ret
two_end:
cmp al, 0x30
jne three_end
mov al, '3'
ret
three_end:
cmp al, 0x40
jne four_end
mov al, '4'
ret
four_end:
cmp al, 0x50
jne five_end
mov al, '5'
ret
five_end:
cmp al, 0x60
jne six_end
mov al, '6'
ret
six_end:
cmp al, 0x70
jne seven_end
mov al, '7'
ret
seven_end:
cmp al, 0x80
jne eight_end
mov al, '8'
ret
eight_end:
cmp al, 0x90
jne nine_end
mov al, '9'
ret
nine_end:
cmp al, 0xa0
jne a_end
mov al, 'A'
ret
a_end:
cmp al, 0xb0
jne b_end
mov al, 'B'
ret
b_end:
cmp al, 0xc0
jne c_end
mov al, 'C'
ret
c_end:
cmp al, 0xd0
jne d_end
mov al, 'D'
ret
d_end:
cmp al, 0xe0
jne e_end
mov al, 'E'
ret
e_end:
cmp al, 0xf0
jne f_end
mov al, 'F'
ret
f_end:
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;The "cls" command;;;;;;;;;;;;;;;;;;;;;;;;;;;;
com_cls:
push ax
push bx
push cx
push dx
mov ax, 0x0700 ; function 07, AL=0 means scroll whole window
mov bh, 0x00 ; character attribute = black
mov cx, 0x0000 ; row = 0, col = 0
mov dx, 0x1e54 ; row = 30 (0x1e), col = 79 (0x4f)
int 0x10 ; call BIOS video interrupt
mov ah, 0x02 ;function 02, set curser position
mov dx, 0x00
int 0x10
pop dx
pop cx
pop bx
pop ax
ret
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
ret
Scan code 0x9E: Break for 'A' key in XT keyboard!
Thanks in advance for the help.
Whenever you need some advice programming an OS, take a look at The OSDev wiki is great!
These two pages will help you:
It is unlikely that you have to deal with an XT keyboard because they where used in the PC-XT that didn't have an 8042 but an 8255 (PPI) chip.
And the PPI responds to ports 60h-63h only, leaving out the 64h which I think you are using.
See this listing.
Don't get confused between keyboard commands and controller commands, from your OS both translate into writes to the same data port but the firsts make their way down to the keyboard, the latter stop at the 8042.
Consider that there are three scan code sets (named set 1, 2 and 3).
The XT used the first, the second one is currently supported by every keyboard, the third is rarely used.
So you have to check which scan code set the keyboard is using, by default it is the second.
Use keyboard command 0f0h with a payload of 00h to known the current scan code (after the usual keyboard ACK 0fah).
If you use a payload of 01h, 02h or 03h you can set the scan code set in use.
Beware that the 8082 by default translate scan code set 2 into scan code set 1, to disable this translation use the controller commands 20h and 60h to clear bit 6 of the Controller Configuration Byte.
So in short:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With