From 7fc34a2e662701c3828f4f7fb18f9d903a0eb7a2 Mon Sep 17 00:00:00 2001 From: Matheus Date: Thu, 22 Sep 2022 14:37:27 -0300 Subject: [PATCH] keyboard: continue the implementation; add shifting support --- src/arch/x86_64/ps2kbd.c | 97 +++++++++++++++++++++++++++- src/include/kernel/keyboard.h | 117 ++++++++++++++++++++++++++++++++++ src/sys/keyboard.c | 67 +++++++++++++++++++ 3 files changed, 278 insertions(+), 3 deletions(-) diff --git a/src/arch/x86_64/ps2kbd.c b/src/arch/x86_64/ps2kbd.c index 5256a210..9fbfb0b6 100644 --- a/src/arch/x86_64/ps2kbd.c +++ b/src/arch/x86_64/ps2kbd.c @@ -34,10 +34,101 @@ static uint8_t ps2cmd(uint8_t cmd){ } -static char asciitable[] = { - 0, '\033', '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', '\b', '\t', 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n', 0, 'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', 0, 0, '\\', 'z', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', '/', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, '7', '8', '9', '-', '4', '5', '6', '+', '4', '1', '2', '3', '0', '.', 0, 0, 0, 0, 0 +static char codes[] = { + KEYCODE_RESERVED, + KEYCODE_ESCAPE, + KEYCODE_1, + KEYCODE_2, + KEYCODE_3, + KEYCODE_4, + KEYCODE_5, + KEYCODE_6, + KEYCODE_7, + KEYCODE_8, + KEYCODE_9, + KEYCODE_0, + KEYCODE_MINUS, + KEYCODE_EQUAL, + KEYCODE_BACKSPACE, + KEYCODE_TAB, + KEYCODE_Q, + KEYCODE_W, + KEYCODE_E, + KEYCODE_R, + KEYCODE_T, + KEYCODE_Y, + KEYCODE_U, + KEYCODE_I, + KEYCODE_O, + KEYCODE_P, + KEYCODE_LEFTBRACE, + KEYCODE_RIGHTBRACE, + KEYCODE_ENTER, + KEYCODE_LEFTCTRL, + KEYCODE_A, + KEYCODE_S, + KEYCODE_D, + KEYCODE_F, + KEYCODE_G, + KEYCODE_H, + KEYCODE_J, + KEYCODE_K, + KEYCODE_L, + KEYCODE_SEMICOLON, + KEYCODE_APOSTROPHE, + KEYCODE_GRAVE, + KEYCODE_LEFTSHIFT, + KEYCODE_BACKSLASH, + KEYCODE_Z, + KEYCODE_X, + KEYCODE_C, + KEYCODE_V, + KEYCODE_B, + KEYCODE_N, + KEYCODE_M, + KEYCODE_COMMA, + KEYCODE_DOT, + KEYCODE_SLASH, + KEYCODE_RIGHTSHIFT, + KEYCODE_KEYPADASTERISK, + KEYCODE_LEFTALT, + KEYCODE_SPACE, + KEYCODE_CAPSLOCK, + KEYCODE_F1, + KEYCODE_F2, + KEYCODE_F3, + KEYCODE_F4, + KEYCODE_F5, + KEYCODE_F6, + KEYCODE_F7, + KEYCODE_F8, + KEYCODE_F9, + KEYCODE_F10, + KEYCODE_NUMLOCK, + KEYCODE_SCROLLLOCK, + KEYCODE_KEYPAD7, + KEYCODE_KEYPAD8, + KEYCODE_KEYPAD9, + KEYCODE_KEYPADMINUS, + KEYCODE_KEYPAD4, + KEYCODE_KEYPAD5, + KEYCODE_KEYPAD6, + KEYCODE_KEYPADPLUS, + KEYCODE_KEYPAD1, + KEYCODE_KEYPAD2, + KEYCODE_KEYPAD3, + KEYCODE_KEYPAD0, + KEYCODE_KEYPADDOT, + 0, 0, 0, + KEYCODE_F11, + KEYCODE_F12 }; +static char extendedcodes[] = { + +}; + + void ps2kbd_irq(){ uint8_t scancode = inb(0x60); if(scancode == 0xE0) @@ -54,7 +145,7 @@ void ps2kbd_irq(){ scancode &= 0x7F; } - packet.ascii = asciitable[scancode]; + packet.keycode = codes[scancode]; keyboard_packet(kb, packet); diff --git a/src/include/kernel/keyboard.h b/src/include/kernel/keyboard.h index 7fb4ac57..6e55e194 100644 --- a/src/include/kernel/keyboard.h +++ b/src/include/kernel/keyboard.h @@ -1,7 +1,124 @@ #ifndef _KEYBOARD_H_INCLUDE #define _KEYBOARD_H_INCLUDE + #define KBPACKET_FLAGS_RELEASED 1 +#define KBPACKET_FLAGS_LEFTCTRL 2 +#define KBPACKET_FLAGS_CAPSLOCK 4 +#define KBPACKET_FLAGS_LEFTALT 8 +#define KBPACKET_FLAGS_RIGHTALT 16 +#define KBPACKET_FLAGS_LEFTSHIFT 32 +#define KBPACKET_FLAGS_RIGHTCTRL 64 +#define KBPACKET_FLAGS_RIGHTSHIFT 128 + + +// linux /dev/input/event keycodes + +#define KEYCODE_RESERVED 0 +#define KEYCODE_ESCAPE 1 +#define KEYCODE_1 2 +#define KEYCODE_2 3 +#define KEYCODE_3 4 +#define KEYCODE_4 5 +#define KEYCODE_5 6 +#define KEYCODE_6 7 +#define KEYCODE_7 8 +#define KEYCODE_8 9 +#define KEYCODE_9 10 +#define KEYCODE_0 11 +#define KEYCODE_MINUS 12 +#define KEYCODE_EQUAL 13 +#define KEYCODE_BACKSPACE 14 +#define KEYCODE_TAB 15 +#define KEYCODE_Q 16 +#define KEYCODE_W 17 +#define KEYCODE_E 18 +#define KEYCODE_R 19 +#define KEYCODE_T 20 +#define KEYCODE_Y 21 +#define KEYCODE_U 22 +#define KEYCODE_I 23 +#define KEYCODE_O 24 +#define KEYCODE_P 25 +#define KEYCODE_LEFTBRACE 26 +#define KEYCODE_RIGHTBRACE 27 +#define KEYCODE_ENTER 28 +#define KEYCODE_LEFTCTRL 29 +#define KEYCODE_A 30 +#define KEYCODE_S 31 +#define KEYCODE_D 32 +#define KEYCODE_F 33 +#define KEYCODE_G 34 +#define KEYCODE_H 35 +#define KEYCODE_J 36 +#define KEYCODE_K 37 +#define KEYCODE_L 38 +#define KEYCODE_SEMICOLON 39 +#define KEYCODE_APOSTROPHE 40 +#define KEYCODE_GRAVE 41 +#define KEYCODE_LEFTSHIFT 42 +#define KEYCODE_BACKSLASH 43 +#define KEYCODE_Z 44 +#define KEYCODE_X 45 +#define KEYCODE_C 46 +#define KEYCODE_V 47 +#define KEYCODE_B 48 +#define KEYCODE_N 49 +#define KEYCODE_M 50 +#define KEYCODE_COMMA 51 +#define KEYCODE_DOT 52 +#define KEYCODE_SLASH 53 +#define KEYCODE_RIGHTSHIFT 54 +#define KEYCODE_KEYPADASTERISK 55 +#define KEYCODE_LEFTALT 56 +#define KEYCODE_SPACE 57 +#define KEYCODE_CAPSLOCK 58 +#define KEYCODE_F1 59 +#define KEYCODE_F2 60 +#define KEYCODE_F3 61 +#define KEYCODE_F4 62 +#define KEYCODE_F5 63 +#define KEYCODE_F6 64 +#define KEYCODE_F7 65 +#define KEYCODE_F8 66 +#define KEYCODE_F9 67 +#define KEYCODE_F10 68 +#define KEYCODE_NUMLOCK 69 +#define KEYCODE_SCROLLLOCK 70 +#define KEYCODE_KEYPAD7 71 +#define KEYCODE_KEYPAD8 72 +#define KEYCODE_KEYPAD9 73 +#define KEYCODE_KEYPADMINUS 74 +#define KEYCODE_KEYPAD4 75 +#define KEYCODE_KEYPAD5 76 +#define KEYCODE_KEYPAD6 77 +#define KEYCODE_KEYPADPLUS 78 +#define KEYCODE_KEYPAD1 79 +#define KEYCODE_KEYPAD2 80 +#define KEYCODE_KEYPAD3 81 +#define KEYCODE_KEYPAD0 82 +#define KEYCODE_KEYPADDOT 83 + + +#define KEYCODE_F11 87 +#define KEYCODE_F12 88 + +#define KEYCODE_KEYPADENTER 96 +#define KEYCODE_RIGHTCTRL 97 +#define KEYCODE_KEYPADSLASH 98 +#define KEYCODE_SYSREQ 99 +#define KEYCODE_RIGHTALT 100 +#define KEYCODE_LINEFEED 101 +#define KEYCODE_HOME 102 +#define KEYCODE_UP 103 +#define KEYCODE_PAGEUP 104 +#define KEYCODE_LEFT 105 +#define KEYCODE_RIGHT 106 +#define KEYCODE_END 107 +#define KEYCODE_DOWN 108 +#define KEYCODE_PAGEDOWN 109 +#define KEYCODE_INSERT 110 +#define KEYCODE_DELETE 111 #include #include diff --git a/src/sys/keyboard.c b/src/sys/keyboard.c index c227659c..512c414a 100644 --- a/src/sys/keyboard.c +++ b/src/sys/keyboard.c @@ -4,10 +4,77 @@ #define MAX_KEYBOARD_COUNT 32 +// XXX this maybe should be strings rather than chars, as +// some keys are sent to the applications in escape sequences + +static char asciitable[] = { + 0, '\033', '1', '2', '3', '4', '5', '6', '7', '8', '9', '0', '-', '=', '\b', '\t', 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n', 0, 'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', '`', 0, '\\', 'z', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', '/', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, '7', '8', '9', '-', '4', '5', '6', '+', '4', '1', '2', '3', '0', '.', 0, 0, 0, 0, 0 +}; + +static char asciitableupper[] = { + 0, '\033', '!', '@', '#', '$', '%', '^', '&', '*', '(', ')', '_', '+', '\b', '\t', 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n', 0, 'A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '\"', '~', 0, '|', 'Z', 'X', 'C', 'V', 'B', 'N', 'M', '<', '>', '?', 0, '*', 0, ' ', 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, '7', '8', '9', '-', '4', '5', '6', '+', '4', '1', '2', '3', '0', '.', 0, 0, 0, 0, 0 +}; + static uint32_t kblist; static keyboard_t keyboards[MAX_KEYBOARD_COUNT]; void keyboard_packet(int kb, kbpacket_t packet){ + + switch(packet.keycode){ + case KEYCODE_LEFTCTRL: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_LEFTCTRL; + else + keyboards[kb].flags |= KBPACKET_FLAGS_LEFTCTRL; + break; + case KEYCODE_RIGHTCTRL: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_RIGHTCTRL; + else + keyboards[kb].flags |= KBPACKET_FLAGS_RIGHTCTRL; + break; + case KEYCODE_CAPSLOCK: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_CAPSLOCK; + else + keyboards[kb].flags |= KBPACKET_FLAGS_CAPSLOCK; + break; + case KEYCODE_LEFTALT: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_LEFTALT; + else + keyboards[kb].flags |= KBPACKET_FLAGS_LEFTALT; + break; + case KEYCODE_RIGHTALT: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_RIGHTALT; + else + keyboards[kb].flags |= KBPACKET_FLAGS_RIGHTALT; + break; + case KEYCODE_LEFTSHIFT: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_LEFTSHIFT; + else + keyboards[kb].flags |= KBPACKET_FLAGS_LEFTSHIFT; + break; + case KEYCODE_RIGHTSHIFT: + if(packet.flags & KBPACKET_FLAGS_RELEASED) + keyboards[kb].flags &= ~KBPACKET_FLAGS_RIGHTSHIFT; + else + keyboards[kb].flags |= KBPACKET_FLAGS_RIGHTSHIFT; + break; + } + + packet.flags |= keyboards[kb].flags; + + char* table = asciitable; + + if( (packet.flags & KBPACKET_FLAGS_LEFTSHIFT) || + (packet.flags & KBPACKET_FLAGS_RIGHTSHIFT)) + table = asciitableupper; + + packet.ascii = table[packet.keycode]; + ringbuffer_write(&keyboards[kb].buffer, &packet, sizeof(kbpacket_t)); event_signal(&keyboards[kb].event, false); }