--- /dev/null
+\r
+#include "core.h"\r
+\r
+uint kbd_data0;\r
+DATA_FIFO32 *kbd_fifo;\r
+\r
+union STATE_KEYLOCK {\r
+ uchar keylock;\r
+ struct STATE_KEYLOCK_KEY {\r
+ unsigned scroll : 1;\r
+ unsigned num : 1;\r
+ unsigned caps : 1;\r
+ } key;\r
+} state_keylock;\r
+\r
+union STATE_KEYSHIFT {\r
+ uchar keyshift;\r
+ struct STATE_KEYSHIFT_KEY {\r
+ unsigned L : 1;\r
+ unsigned R : 1;\r
+ } key;\r
+} state_keyshift;\r
+\r
+union STATE_KEYCTRL {\r
+ uchar keyctrl;\r
+ struct STATE_KEYCTRL_KEY {\r
+ unsigned L : 1;\r
+ unsigned R : 1;\r
+ } key;\r
+} state_keyctrl;\r
+\r
+union STATE_KEYALT {\r
+ uchar keyalt;\r
+ struct STATE_KEYALT_KEY {\r
+ unsigned L : 1;\r
+ unsigned R : 1;\r
+ } key;\r
+} state_keyalt;\r
+\r
+ushort state_shift;\r
+\r
+uint key_decode_phase;\r
+uchar key_decode_buf[4];\r
+uchar kbc_retv;\r
+\r
+/*\83L\81[\83R\81[\83h\95Ï\8a·\83e\81[\83u\83\8b*/\r
+ushort Keyboard_KeyCodeTable[0x80] = {\r
+ KEYID_MASK_EXTENDED | KEYID_KBD_ERROR,\r
+ KEYID_MASK_EXTENDED | KEYID_ESC,\r
+ '1',\r
+ '2',\r
+ '3',\r
+ '4',\r
+ '5',\r
+ '6',\r
+ '7',\r
+ '8',\r
+ '9',\r
+ '0',\r
+ '-',\r
+ '^',\r
+ KEYID_MASK_EXTENDED | KEYID_BACKSPACE,\r
+ KEYID_MASK_EXTENDED | KEYID_TAB,\r
+/*0x10*/\r
+ 'Q',\r
+ 'W',\r
+ 'E',\r
+ 'R',\r
+ 'T',\r
+ 'Y',\r
+ 'U',\r
+ 'I',\r
+ 'O',\r
+ 'P',\r
+ '@',\r
+ '[',\r
+ KEYID_MASK_EXTENDED | KEYID_ENTER,\r
+ KEYID_MASK_EXTENDED | KEYID_CTRL_L,\r
+ 'A',\r
+ 'S',\r
+/*0x20*/\r
+ 'D',\r
+ 'F',\r
+ 'G',\r
+ 'H',\r
+ 'J',\r
+ 'K',\r
+ 'L',\r
+ ';',\r
+ ':',\r
+ KEYID_MASK_EXTENDED | KEYID_KANJI,\r
+ KEYID_MASK_EXTENDED | KEYID_SHIFT_L,\r
+ ']',\r
+ 'Z',\r
+ 'X',\r
+ 'C',\r
+ 'V',\r
+/*0x30*/\r
+ 'B',\r
+ 'N',\r
+ 'M',\r
+ ',',\r
+ '.',\r
+ '/',\r
+ KEYID_MASK_EXTENDED | KEYID_SHIFT_R,\r
+ KEYID_MASK_TENKEY | '*',\r
+ KEYID_MASK_EXTENDED | KEYID_ALT_L,\r
+ ' ',\r
+ KEYID_MASK_EXTENDED | KEYID_LOCK_CAPS,\r
+ KEYID_MASK_EXTENDED | KEYID_F1,\r
+ KEYID_MASK_EXTENDED | KEYID_F2,\r
+ KEYID_MASK_EXTENDED | KEYID_F3,\r
+ KEYID_MASK_EXTENDED | KEYID_F4,\r
+ KEYID_MASK_EXTENDED | KEYID_F5,\r
+/*0x40*/\r
+ KEYID_MASK_EXTENDED | KEYID_F6,\r
+ KEYID_MASK_EXTENDED | KEYID_F7,\r
+ KEYID_MASK_EXTENDED | KEYID_F8,\r
+ KEYID_MASK_EXTENDED | KEYID_F9,\r
+ KEYID_MASK_EXTENDED | KEYID_F10,\r
+ KEYID_MASK_EXTENDED | KEYID_LOCK_NUM,\r
+ KEYID_MASK_EXTENDED | KEYID_LOCK_SCROOL,\r
+ KEYID_MASK_TENKEY | '7',\r
+ KEYID_MASK_TENKEY | '8',\r
+ KEYID_MASK_TENKEY | '9',\r
+ KEYID_MASK_TENKEY | '-',\r
+ KEYID_MASK_TENKEY | '4',\r
+ KEYID_MASK_TENKEY | '5',\r
+ KEYID_MASK_TENKEY | '6',\r
+ KEYID_MASK_TENKEY | '+',\r
+ KEYID_MASK_TENKEY | '1',\r
+/*0x50*/\r
+ KEYID_MASK_TENKEY | '2',\r
+ KEYID_MASK_TENKEY | '3',\r
+ KEYID_MASK_TENKEY | '0',\r
+ KEYID_MASK_TENKEY | '.',\r
+ KEYID_MASK_EXTENDED | KEYID_SYS_RQ,\r
+ 0x0000,\r
+ 0x0000,\r
+ KEYID_MASK_EXTENDED | KEYID_F11,\r
+ KEYID_MASK_EXTENDED | KEYID_F12,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+/*0x60*/\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+/*0x70*/\r
+ KEYID_MASK_EXTENDED | KEYID_HIRAGANA,\r
+ 0x0000,\r
+ 0x0000,\r
+ '_',\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ 0x0000,\r
+ KEYID_MASK_EXTENDED | KEYID_HENKAN,\r
+ 0x0000,\r
+ KEYID_MASK_EXTENDED | KEYID_MUHENKAN,\r
+ 0x0000,\r
+ '\\',\r
+// 0x5c, // ='\' for mikan-trap.\r
+ 0x0000,\r
+ 0x0000\r
+};\r
+\r
+//\83[\83\8d\82Ì\8f\8a\82Í\83V\83t\83g\95¶\8e\9a\82ª\96³\82¢\82Ì\82Å\81A\83e\81[\83u\83\8b0\82ð\8eQ\8fÆ\r
+uchar Keyboard_KeyCodeTable_Shift[0x80] = {\r
+ 0x00,\r
+ 0x00,\r
+ '!',\r
+ 0x22, //double quote\r
+ '#',\r
+ '$',\r
+ '%',\r
+ '&',\r
+ 0x27, //single quote\r
+ '(',\r
+ ')',\r
+ '~',\r
+ '=',\r
+ '~',\r
+ 0x00,\r
+ 0x00,\r
+/*0x10*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ '`',\r
+ '{',\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x20*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ '+',\r
+ '*',\r
+ 0x00,\r
+ 0x00,\r
+ '}',\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x30*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ '<',\r
+ '>',\r
+ '?',\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x40*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x50*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x60*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+/*0x70*/\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ '_',\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ 0x00,\r
+ '|',\r
+ 0x00,\r
+ 0x00\r
+};\r
+\r
+void Initialize_Keyboard(void)\r
+{\r
+ System_GateDescriptor_Set(0x21, (uint)asm_InterruptHandler21, 0x02, AR_INTGATE32);\r
+ ProgrammableInterruptController_InterruptMask_Clear(0x01);\r
+ kbd_data0 = 0;\r
+ kbd_fifo = 0;\r
+ state_keylock.keylock = 0;\r
+ state_keyshift.keyshift = 0;\r
+ state_keyctrl.keyctrl = 0;\r
+ state_keyalt.keyalt = 0;\r
+ key_decode_phase = 0;\r
+\r
+ KeyboardController_Wait_SendReady();\r
+ IO_Out8(PORT_KEYCMD, KEYCMD_WRITE_8042_MODE_REG);\r
+ KeyboardController_Wait_SendReady();\r
+ IO_Out8(PORT_KEYDATA, KBC_MODE);\r
+\r
+ return;\r
+}\r
+\r
+void InterruptHandler21(uint *esp)\r
+{\r
+ uint data;\r
+\r
+ data = IO_In8(PORT_KEYDATA);\r
+\r
+ ProgrammableInterruptController_InterruptRequest_Complete(0x01);\r
+\r
+ if(kbd_fifo != 0){\r
+ FIFO32_Put(kbd_fifo, data + kbd_data0);\r
+ }\r
+\r
+ if(data == KEYDATA_ACK || data == KEYDATA_RESEND){\r
+ kbc_retv = data;\r
+ }\r
+\r
+ return;\r
+}\r
+\r
+void Keyboard_Set_ReceiveFIFO(DATA_FIFO32 *fifo, uint data0)\r
+{\r
+ kbd_data0 = data0;\r
+ kbd_fifo = fifo;\r
+\r
+ return; \r
+}\r
+\r
+ushort Keyboard_Decode_KeyCode(uchar keycode)\r
+{\r
+ ushort keyid;\r
+ ushort table;\r
+ keyid = 0;\r
+ table = 0;\r
+\r
+ if(keycode == KEYDATA_ACK || keycode == KEYDATA_RESEND){\r
+ return 0;\r
+ }\r
+\r
+ key_decode_buf[key_decode_phase] = keycode;\r
+\r
+ switch(key_decode_phase){\r
+ case 0:\r
+\r
+ if(key_decode_buf[0] == 0xe0){\r
+ key_decode_phase = 1;\r
+ break;\r
+ } else if(key_decode_buf[0] == 0xe1){\r
+ key_decode_phase = 2;\r
+ break;\r
+ } else{\r
+ if(state_keylock.key.caps){\r
+ if(!state_keyshift.keyshift){\r
+ table = 1;\r
+ }\r
+ } else{\r
+ if(state_keyshift.keyshift){\r
+ table = 1;\r
+ }\r
+ }\r
+\r
+ if(state_keyshift.keyshift){\r
+ keyid = Keyboard_KeyCodeTable_Shift[(key_decode_buf[0] & KEYID_MASK_ID)];\r
+ if(keyid == 0){\r
+ keyid = Keyboard_KeyCodeTable[(key_decode_buf[0] & KEYID_MASK_ID)];\r
+ }\r
+ } else{\r
+ keyid = Keyboard_KeyCodeTable[(key_decode_buf[0] & KEYID_MASK_ID)];\r
+ }\r
+\r
+ if(!table && ('A' <= keyid && keyid <= 'Z')){\r
+ keyid += 0x20;\r
+ }\r
+\r
+ if(keyid & KEYID_MASK_EXTENDED){\r
+ if(keyid == (KEYID_MASK_EXTENDED | KEYID_CTRL_L)){\r
+ if((key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ state_keyctrl.key.L = False;\r
+ } else{\r
+ state_keyctrl.key.L = True;\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_SHIFT_L)){\r
+ if((key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ state_keyshift.key.L = False;\r
+ } else{\r
+ state_keyshift.key.L = True;\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_SHIFT_R)){\r
+ if((key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ state_keyshift.key.R = False;\r
+ } else{\r
+ state_keyshift.key.R = True;\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_ALT_L)){\r
+ if((key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ state_keyalt.key.L = False;\r
+ } else{\r
+ state_keyalt.key.L = True;\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_LOCK_CAPS)){\r
+ if(!(key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ if(state_keylock.key.caps){\r
+ state_keylock.key.caps = False;\r
+ } else{\r
+ state_keylock.key.caps = True;\r
+ }\r
+ KeyboardController_SetLED(state_keylock.keylock);\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_LOCK_NUM)){\r
+ if(!(key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ if(state_keylock.key.num){\r
+ state_keylock.key.num = False;\r
+ } else{\r
+ state_keylock.key.num = True;\r
+ }\r
+ KeyboardController_SetLED(state_keylock.keylock);\r
+ }\r
+ } else if(keyid == (KEYID_MASK_EXTENDED | KEYID_LOCK_SCROOL)){\r
+ if(!(key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ if(state_keylock.key.scroll){\r
+ state_keylock.key.scroll = False;\r
+ } else{\r
+ state_keylock.key.scroll = True;\r
+ }\r
+ KeyboardController_SetLED(state_keylock.keylock);\r
+ }\r
+ }\r
+ }\r
+\r
+ if(keyid != 0 && (key_decode_buf[0] & KEYID_MASK_BREAK)){\r
+ keyid |= KEYID_MASK_BREAK;\r
+ }\r
+\r
+ }\r
+ key_decode_phase = 0;\r
+ break;\r
+ case 1: //E0\8ag\92£\83L\81[\83R\81[\83h\r
+ if((key_decode_buf[1] & KEYID_MASK_ID) == 0x1c){\r
+ keyid |= KEYID_MASK_TENKEY | KEYID_ENTER;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x1d){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_CTRL_R;\r
+ if((key_decode_buf[1] & KEYID_MASK_BREAK)){\r
+ state_keyctrl.key.R = False;\r
+ } else{\r
+ state_keyctrl.key.R = True;\r
+ }\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x35){\r
+ keyid |= KEYID_MASK_TENKEY | '/';\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x37){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_PRINT_SCREEN;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x38){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_ALT_R;\r
+ if((key_decode_buf[1] & KEYID_MASK_BREAK)){\r
+ state_keyalt.key.R = False;\r
+ } else{\r
+ state_keyalt.key.R = True;\r
+ }\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x46){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_BREAK;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x47){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_HOME;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x48){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_CURSOR_U;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x49){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_PAGE_UP;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x4b){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_CURSOR_L;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x4d){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_CURSOR_R;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x4f){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_END;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x50){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_CURSOR_D;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x51){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_PAGE_DOWN;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x52){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_INSERT;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x53){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_DELETE;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x5b){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_ICON_L;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x5c){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_ICON_R;\r
+ } else if((key_decode_buf[1] & KEYID_MASK_ID) == 0x5d){\r
+ keyid |= KEYID_MASK_EXTENDED | KEYID_MENU;\r
+ }\r
+\r
+ if(keyid != 0 && (key_decode_buf[1] & KEYID_MASK_BREAK)){\r
+ keyid |= KEYID_MASK_BREAK;\r
+ }\r
+\r
+ key_decode_phase = 0;\r
+ break;\r
+ case 2: //E1\8ag\92£\83L\81[\83R\81[\83h\83t\83F\81[\83Y0\r
+ key_decode_phase = 3;\r
+ break;\r
+ case 3: //E1\8ag\92£\83L\81[\83R\81[\83h\83t\83F\81[\83Y1\r
+ if((key_decode_buf[1] == 0x1d) && (key_decode_buf[2] == 0x45)){ //Pause-Key Make\r
+ keyid = KEYID_MASK_EXTENDED | KEYID_PAUSE;\r
+ } else if((key_decode_buf[1] == 0x9d) && (key_decode_buf[2] == 0xc5)){ //Pause-Key Break\r
+ keyid = KEYID_MASK_EXTENDED | KEYID_MASK_BREAK | KEYID_PAUSE;\r
+ }\r
+ key_decode_phase = 0;\r
+ break;\r
+ }\r
+\r
+ if(keyid != 0){\r
+ if(state_keyshift.keyshift){\r
+ keyid |= KEYID_MASK_STATE_SHIFT;\r
+ }\r
+ if(state_keyctrl.keyctrl){\r
+ keyid |= KEYID_MASK_STATE_CTRL;\r
+ }\r
+ if(state_keyalt.keyalt){\r
+ keyid |= KEYID_MASK_STATE_ALT;\r
+ }\r
+ keyid |= ((ushort)state_keylock.keylock << 12);\r
+ }\r
+\r
+ return keyid;\r
+}\r
+\r
+void KeyboardController_SetLED(uchar leds)\r
+{\r
+ KeyboardController_SendData(KEYCMD_LED);\r
+ KeyboardController_SendData(leds);\r
+ return;\r
+}\r
+\r
+void KeyboardController_Wait_SendReady(void)\r
+{\r
+ for(;;){\r
+ if((IO_In8(PORT_KEYSTA) & KEYSTA_SEND_NOTREADY) == 0) {\r
+ break;\r
+ }\r
+ }\r
+ return;\r
+}\r
+\r
+void KeyboardController_SendData(uchar data)\r
+{\r
+ for(;;){\r
+ kbc_retv = 0;\r
+ KeyboardController_Wait_SendReady();\r
+ IO_Out8(PORT_KEYDATA, data);\r
+ for(;;){\r
+ if(kbc_retv == KEYDATA_ACK){\r
+ return;\r
+ }\r
+ if(kbc_retv == KEYDATA_RESEND){\r
+ break;\r
+ }\r
+ }\r
+ }\r
+}\r
+\r
+void KeyboardController_SendCommand(uchar cmd)\r
+{\r
+ for(;;){\r
+ kbc_retv = 0;\r
+ KeyboardController_Wait_SendReady();\r
+ IO_Out8(PORT_KEYCMD, cmd);\r
+ for(;;){\r
+ if(kbc_retv == KEYDATA_ACK){\r
+ return;\r
+ }\r
+ if(kbc_retv == KEYDATA_RESEND){\r
+ break;\r
+ }\r
+ }\r
+ }\r
+}\r