]> pd.if.org Git - zos/blob - kbd.c
add a readme with a public domain note
[zos] / kbd.c
1 #include <stdint.h>
2
3 #include "kernel.h"
4 #include "kbd.h"
5 #include "interrupt.h"
6 #include "tty.h"
7 #include "pic.h"
8 #include "ioport.h"
9
10 static struct interrupt_handler keyboard;
11
12 static unsigned char keymap[128] = {
13   0, 27, '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', '\b',
14   '\t', 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n',
15   0, 'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', '`',
16   0, '\\', 'z', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', '/', 0,
17   '*', '0', ' ', 0,
18   0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
19   0, 0, 0, 0, 0, '-', 0, 0, 0, '+',
20   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
21 };
22
23 static unsigned char keymap_shift[128] = {
24   0, 27, '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', '\b',
25   '\t', 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n',
26   0, 'A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '"', '~',
27   0, '|', 'Z', 'X', 'C', 'V', 'B', 'N', 'M', '<', '>', '?', 0,
28   '*', '0', ' ', 0,
29   0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
30   0, 0, 0, 0, 0, '-', 0, 0, 0, '+',
31   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
32 };
33
34 static unsigned int kbd_state = 0;
35
36 static unsigned char keyboard_decode(unsigned char scancode) {
37         if (scancode & 0x80) {
38                 /* break */
39                 scancode = scancode & 0x7F;
40                 if (scancode == 0x2A || scancode == 0x36) {
41                         /* left or right shift */
42                         kbd_state = 0;
43                 }
44                 return 0;
45         } else {
46                 if (scancode == 0x2A || scancode == 0x36) {
47                         kbd_state = 1;
48                         return 0;
49                 }
50     
51                 if (kbd_state == 1) {
52                         return keymap_shift[scancode];
53                 } else {
54                         return keymap[scancode];
55                 }
56         }
57 }
58
59 static void keyboard_handler(struct interrupt_context *c, void *unused) {
60         unsigned char code;
61         unsigned char scancode;
62
63         scancode = inport8(0x60);
64
65         code = keyboard_decode(scancode);
66
67         /* TODO deliver to process with console open */
68         /* will need a notion of 'foreground' and 'background' processes */
69         /* might make sense to just hand it off to whatever terminal it is
70          * attached to
71          */
72         if(code) {
73                 printk("%c", code);
74         }
75         code = scancode;
76 }
77
78 void init_keyboard() {
79         keyboard.handler = keyboard_handler;
80         keyboard.context = 0;
81
82         interrupt_add_handler(IRQ1, &keyboard);
83 }