15 CHAR16 ShiftUnicodeChar;
16} ConvertKeyboardScanCodeToEfiKey[] = {
556UINTN mWaitForValueTimeOut = KEYBOARD_WAITFORVALUE_TIMEOUT;
558BOOLEAN mEnableMouseInterface;
572 if (Queue->Head <= Queue->Tail) {
573 return Queue->Tail - Queue->Head;
575 return Queue->Tail + KEYBOARD_SCAN_CODE_MAX_COUNT - Queue->Head;
605 return EFI_NOT_READY;
611 for (Index = 0, Pos = Queue->Head; Index < Count; Index++, Pos = (Pos + 1) % KEYBOARD_SCAN_CODE_MAX_COUNT) {
612 Buf[Index] = Queue->Buffer[Pos];
634 OUT UINT8 *Buf OPTIONAL
643 return EFI_NOT_READY;
649 for (Index = 0; Index < Count; Index++, Queue->Head = (Queue->Head + 1) % KEYBOARD_SCAN_CODE_MAX_COUNT) {
651 Buf[Index] = Queue->Buffer[Queue->Head];
674 Queue->Buffer[Queue->Tail] = Scancode;
675 Queue->Tail = (Queue->Tail + 1) % KEYBOARD_SCAN_CODE_MAX_COUNT;
692 return IoRead8 (ConsoleIn->DataRegisterAddress);
708 IoWrite8 (ConsoleIn->DataRegisterAddress, Data);
724 return IoRead8 (ConsoleIn->StatusRegisterAddress);
740 IoWrite8 (ConsoleIn->CommandRegisterAddress, Data);
756 ConsoleIn->KeyboardErr =
TRUE;
787 OldTpl =
gBS->RaiseTPL (TPL_NOTIFY);
793 gBS->RestoreTPL (OldTpl);
821 gBS->RestoreTPL (OldTpl);
850 for (TimeOut = 0; TimeOut < KEYBOARD_TIMEOUT; TimeOut += 30) {
860 if (RegFilled == 0) {
892 for (TimeOut = 0; TimeOut < KEYBOARD_TIMEOUT; TimeOut += 30) {
901 if (RegEmptied == 0) {
938 for (TimeOut = 0; TimeOut < KEYBOARD_TIMEOUT; TimeOut += 30) {
947 if (RegEmptied == 0) {
960 for (TimeOut = 0; TimeOut < KEYBOARD_TIMEOUT; TimeOut += 30) {
969 if (RegEmptied == 0) {
1007 if (Data == Value) {
1020 for (TimeOut = 0; TimeOut < KEYBOARD_TIMEOUT; TimeOut += 30) {
1029 SumTimeOut += TimeOut;
1031 if (Data == Value) {
1036 if (SumTimeOut >= mWaitForValueTimeOut) {
1072 if (EFI_ERROR (Status)) {
1082 if (ConsoleIn->CapsLock) {
1086 if (ConsoleIn->NumLock) {
1090 if (ConsoleIn->ScrollLock) {
1096 if (EFI_ERROR (Status)) {
1116 KeyState->KeyShiftState = EFI_SHIFT_STATE_VALID
1117 | (ConsoleIn->LeftCtrl ? EFI_LEFT_CONTROL_PRESSED : 0)
1118 | (ConsoleIn->RightCtrl ? EFI_RIGHT_CONTROL_PRESSED : 0)
1119 | (ConsoleIn->LeftAlt ? EFI_LEFT_ALT_PRESSED : 0)
1120 | (ConsoleIn->RightAlt ? EFI_RIGHT_ALT_PRESSED : 0)
1121 | (ConsoleIn->LeftShift ? EFI_LEFT_SHIFT_PRESSED : 0)
1122 | (ConsoleIn->RightShift ? EFI_RIGHT_SHIFT_PRESSED : 0)
1123 | (ConsoleIn->LeftLogo ? EFI_LEFT_LOGO_PRESSED : 0)
1124 | (ConsoleIn->RightLogo ? EFI_RIGHT_LOGO_PRESSED : 0)
1125 | (ConsoleIn->Menu ? EFI_MENU_KEY_PRESSED : 0)
1126 | (ConsoleIn->SysReq ? EFI_SYS_REQ_PRESSED : 0)
1128 KeyState->KeyToggleState = EFI_TOGGLE_STATE_VALID
1129 | (ConsoleIn->CapsLock ? EFI_CAPS_LOCK_ACTIVE : 0)
1130 | (ConsoleIn->NumLock ? EFI_NUM_LOCK_ACTIVE : 0)
1131 | (ConsoleIn->ScrollLock ? EFI_SCROLL_LOCK_ACTIVE : 0)
1132 | (ConsoleIn->IsSupportPartialKey ? EFI_KEY_STATE_EXPOSED : 0)
1160 UINT8 ScancodeArr[3];
1161 UINT32 ScancodeArrPos;
1171 Status =
GetScancodeBufHead (&ConsoleIn->ScancodeQueue, ScancodeArrPos + 1, ScancodeArr);
1172 if (EFI_ERROR (Status)) {
1176 if (ScancodeArr[ScancodeArrPos] == SCANCODE_EXTENDED0) {
1182 Status =
GetScancodeBufHead (&ConsoleIn->ScancodeQueue, ScancodeArrPos + 1, ScancodeArr);
1183 if (EFI_ERROR (Status)) {
1186 }
else if (ScancodeArr[ScancodeArrPos] == SCANCODE_EXTENDED1) {
1192 Status =
GetScancodeBufHead (&ConsoleIn->ScancodeQueue, ScancodeArrPos + 1, ScancodeArr);
1193 if (EFI_ERROR (Status)) {
1201 Status =
PopScancodeBufHead (&ConsoleIn->ScancodeQueue, ScancodeArrPos + 1, ScancodeArr);
1207 ScanCode = ScancodeArr[ScancodeArrPos];
1214 case SCANCODE_CTRL_MAKE:
1216 ConsoleIn->RightCtrl =
TRUE;
1218 ConsoleIn->LeftCtrl =
TRUE;
1222 case SCANCODE_CTRL_BREAK:
1224 ConsoleIn->RightCtrl =
FALSE;
1226 ConsoleIn->LeftCtrl =
FALSE;
1231 case SCANCODE_ALT_MAKE:
1233 ConsoleIn->RightAlt =
TRUE;
1235 ConsoleIn->LeftAlt =
TRUE;
1239 case SCANCODE_ALT_BREAK:
1241 ConsoleIn->RightAlt =
FALSE;
1243 ConsoleIn->LeftAlt =
FALSE;
1248 case SCANCODE_LEFT_SHIFT_MAKE:
1255 ConsoleIn->LeftShift =
TRUE;
1261 case SCANCODE_LEFT_SHIFT_BREAK:
1263 ConsoleIn->LeftShift =
FALSE;
1268 case SCANCODE_RIGHT_SHIFT_MAKE:
1269 ConsoleIn->RightShift =
TRUE;
1271 case SCANCODE_RIGHT_SHIFT_BREAK:
1272 ConsoleIn->RightShift =
FALSE;
1275 case SCANCODE_LEFT_LOGO_MAKE:
1276 ConsoleIn->LeftLogo =
TRUE;
1278 case SCANCODE_LEFT_LOGO_BREAK:
1279 ConsoleIn->LeftLogo =
FALSE;
1282 case SCANCODE_RIGHT_LOGO_MAKE:
1283 ConsoleIn->RightLogo =
TRUE;
1285 case SCANCODE_RIGHT_LOGO_BREAK:
1286 ConsoleIn->RightLogo =
FALSE;
1289 case SCANCODE_MENU_MAKE:
1290 ConsoleIn->Menu =
TRUE;
1292 case SCANCODE_MENU_BREAK:
1293 ConsoleIn->Menu =
FALSE;
1296 case SCANCODE_SYS_REQ_MAKE:
1298 ConsoleIn->SysReq =
TRUE;
1302 case SCANCODE_SYS_REQ_BREAK:
1304 ConsoleIn->SysReq =
FALSE;
1309 case SCANCODE_SYS_REQ_MAKE_WITH_ALT:
1310 ConsoleIn->SysReq =
TRUE;
1312 case SCANCODE_SYS_REQ_BREAK_WITH_ALT:
1313 ConsoleIn->SysReq =
FALSE;
1316 case SCANCODE_CAPS_LOCK_MAKE:
1317 ConsoleIn->CapsLock = (BOOLEAN) !ConsoleIn->CapsLock;
1320 case SCANCODE_NUM_LOCK_MAKE:
1321 ConsoleIn->NumLock = (BOOLEAN) !ConsoleIn->NumLock;
1324 case SCANCODE_SCROLL_LOCK_MAKE:
1326 ConsoleIn->ScrollLock = (BOOLEAN) !ConsoleIn->ScrollLock;
1337 if (
ScanCode >= SCANCODE_MAX_MAKE) {
1347 if ((ConsoleIn->LeftCtrl || ConsoleIn->RightCtrl) &&
1348 (ConsoleIn->LeftAlt || ConsoleIn->RightAlt) &&
1359 KeyData.
Key.ScanCode = SCAN_NULL;
1360 KeyData.
Key.UnicodeChar = CHAR_NULL;
1365 if (Extend0 && (
ScanCode == 0x35)) {
1366 KeyData.
Key.UnicodeChar = L
'/';
1367 KeyData.
Key.ScanCode = SCAN_NULL;
1372 }
else if (Extend1 && (
ScanCode == SCANCODE_NUM_LOCK_MAKE)) {
1373 KeyData.
Key.UnicodeChar = CHAR_NULL;
1374 KeyData.
Key.ScanCode = SCAN_PAUSE;
1379 }
else if (Extend0 && (
ScanCode == SCANCODE_SCROLL_LOCK_MAKE)) {
1380 KeyData.
Key.UnicodeChar = CHAR_NULL;
1381 KeyData.
Key.ScanCode = SCAN_PAUSE;
1386 }
else if (Extend0 && (
ScanCode == SCANCODE_SYS_REQ_MAKE)) {
1387 KeyData.
Key.UnicodeChar = CHAR_NULL;
1388 KeyData.
Key.ScanCode = SCAN_NULL;
1394 for (Index = 0; ConvertKeyboardScanCodeToEfiKey[Index].ScanCode != TABLE_END; Index++) {
1396 KeyData.
Key.ScanCode = ConvertKeyboardScanCodeToEfiKey[Index].EfiScanCode;
1397 KeyData.
Key.UnicodeChar = ConvertKeyboardScanCodeToEfiKey[Index].UnicodeChar;
1399 if ((ConsoleIn->LeftShift || ConsoleIn->RightShift) &&
1400 (ConvertKeyboardScanCodeToEfiKey[Index].UnicodeChar != ConvertKeyboardScanCodeToEfiKey[Index].ShiftUnicodeChar))
1402 KeyData.
Key.UnicodeChar = ConvertKeyboardScanCodeToEfiKey[Index].ShiftUnicodeChar;
1413 if (ConsoleIn->CapsLock) {
1414 if ((KeyData.
Key.UnicodeChar >= L
'a') && (KeyData.
Key.UnicodeChar <= L
'z')) {
1415 KeyData.
Key.UnicodeChar = (UINT16)(KeyData.
Key.UnicodeChar - L
'a' + L
'A');
1416 }
else if ((KeyData.
Key.UnicodeChar >= L
'A') && (KeyData.
Key.UnicodeChar <= L
'Z')) {
1417 KeyData.
Key.UnicodeChar = (UINT16)(KeyData.
Key.UnicodeChar - L
'A' + L
'a');
1430 if (ConsoleIn->NumLock && !(ConsoleIn->LeftShift || ConsoleIn->RightShift) && !Extend0) {
1431 KeyData.
Key.ScanCode = SCAN_NULL;
1433 KeyData.
Key.UnicodeChar = CHAR_NULL;
1440 if ((KeyData.
Key.ScanCode == SCAN_NULL) && (KeyData.
Key.UnicodeChar == CHAR_NULL)) {
1441 if (!ConsoleIn->IsSupportPartialKey) {
1449 for (Link =
GetFirstNode (&ConsoleIn->NotifyList); !
IsNull (&ConsoleIn->NotifyList, Link); Link =
GetNextNode (&ConsoleIn->NotifyList, Link)) {
1450 CurrentNotify =
CR (
1454 KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE
1463 gBS->SignalEvent (ConsoleIn->KeyNotifyProcessEvent);
1485 IN BOOLEAN ExtendedVerification
1495 mEnableMouseInterface =
TRUE;
1501 gBS->LocateProtocol (
1502 &gEfiPs2PolicyProtocolGuid,
1510 ConsoleIn->DevicePath
1518 while (!EFI_ERROR (Status) && TryTime < KEYBOARD_MAX_TRY) {
1526 if (TryTime == KEYBOARD_MAX_TRY) {
1527 Status = EFI_DEVICE_ERROR;
1555 if (EFI_ERROR (Status)) {
1561 if (EFI_ERROR (Status)) {
1569 if ((CommandByte & 0x20) != 0) {
1570 mEnableMouseInterface =
FALSE;
1572 mEnableMouseInterface =
TRUE;
1575 mEnableMouseInterface =
FALSE;
1587 Status =
KeyboardCommand (ConsoleIn, KEYBOARD_8042_COMMAND_DISABLE_KEYBOARD_INTERFACE);
1588 if (EFI_ERROR (Status)) {
1593 Status =
KeyboardCommand (ConsoleIn, KEYBOARD_8042_COMMAND_DISABLE_MOUSE_INTERFACE);
1594 if (EFI_ERROR (Status)) {
1601 EFI_PERIPHERAL_KEYBOARD | EFI_P_KEYBOARD_PC_SELF_TEST,
1602 ConsoleIn->DevicePath
1607 Status =
KeyboardCommand (ConsoleIn, KEYBOARD_8042_COMMAND_CONTROLLER_SELF_TEST);
1608 if (EFI_ERROR (Status)) {
1609 KeyboardError (ConsoleIn, L
"8042 controller command write error!\n\r");
1614 if (EFI_ERROR (Status)) {
1615 KeyboardError (ConsoleIn, L
"8042 controller self test failed!\n\r");
1623 mEnableMouseInterface =
FALSE;
1626 if (Ps2Policy !=
NULL) {
1627 Ps2Policy->Ps2InitHardware (ConsoleIn->Handle);
1649 if (EFI_ERROR (Status)) {
1650 KeyboardError (ConsoleIn, L
"8042 controller command write error!\n\r");
1655 if (EFI_ERROR (Status)) {
1656 KeyboardError (ConsoleIn, L
"8042 controller data write error!\n\r");
1663 ConsoleIn->ScancodeQueue.Head = 0;
1664 ConsoleIn->ScancodeQueue.Tail = 0;
1665 ConsoleIn->EfiKeyQueue.Head = 0;
1666 ConsoleIn->EfiKeyQueue.Tail = 0;
1667 ConsoleIn->EfiKeyQueueForNotify.Head = 0;
1668 ConsoleIn->EfiKeyQueueForNotify.Tail = 0;
1673 ConsoleIn->CapsLock =
FALSE;
1674 ConsoleIn->NumLock =
FALSE;
1675 ConsoleIn->ScrollLock =
FALSE;
1676 ConsoleIn->LeftCtrl =
FALSE;
1677 ConsoleIn->RightCtrl =
FALSE;
1678 ConsoleIn->LeftAlt =
FALSE;
1679 ConsoleIn->RightAlt =
FALSE;
1680 ConsoleIn->LeftShift =
FALSE;
1681 ConsoleIn->RightShift =
FALSE;
1682 ConsoleIn->LeftLogo =
FALSE;
1683 ConsoleIn->RightLogo =
FALSE;
1684 ConsoleIn->Menu =
FALSE;
1685 ConsoleIn->SysReq =
FALSE;
1687 ConsoleIn->IsSupportPartialKey =
FALSE;
1701 Status =
KeyboardCommand (ConsoleIn, KEYBOARD_8042_COMMAND_KEYBOARD_INTERFACE_SELF_TEST);
1702 if (EFI_ERROR (Status)) {
1703 KeyboardError (ConsoleIn, L
"8042 controller command write error!\n\r");
1708 if (EFI_ERROR (Status)) {
1711 L
"Some specific value not acquired from 8042 controller!\n\r"
1719 Status =
KeyboardWrite (ConsoleIn, KEYBOARD_8048_COMMAND_RESET);
1720 if (EFI_ERROR (Status)) {
1721 KeyboardError (ConsoleIn, L
"8042 controller data write error!\n\r");
1726 if (EFI_ERROR (Status)) {
1727 KeyboardError (ConsoleIn, L
"Some specific value not acquired from 8042 controller!\n\r");
1736 mWaitForValueTimeOut = KEYBOARD_WAITFORVALUE_TIMEOUT;
1741 Status =
KeyboardWrite (ConsoleIn, KEYBOARD_8048_COMMAND_SELECT_SCAN_CODE_SET);
1742 if (EFI_ERROR (Status)) {
1743 KeyboardError (ConsoleIn, L
"8042 controller data write error!\n\r");
1748 if (EFI_ERROR (Status)) {
1749 KeyboardError (ConsoleIn, L
"Some specific value not acquired from 8042 controller!\n\r");
1754 if (EFI_ERROR (Status)) {
1755 KeyboardError (ConsoleIn, L
"8042 controller data write error!!\n\r");
1760 if (EFI_ERROR (Status)) {
1761 KeyboardError (ConsoleIn, L
"Some specific value not acquired from 8042 controller!\n\r");
1768 Status =
KeyboardWrite (ConsoleIn, KEYBOARD_8048_COMMAND_CLEAR_OUTPUT_DATA);
1769 if (EFI_ERROR (Status)) {
1770 KeyboardError (ConsoleIn, L
"8042 controller data write error!\n\r");
1775 if (EFI_ERROR (Status)) {
1776 KeyboardError (ConsoleIn, L
"Some specific value not acquired from 8042 controller!\n\r");
1781 if (Ps2Policy !=
NULL) {
1782 if ((Ps2Policy->KeyboardLight & EFI_KEYBOARD_CAPSLOCK) == EFI_KEYBOARD_CAPSLOCK) {
1783 ConsoleIn->CapsLock =
TRUE;
1786 if ((Ps2Policy->KeyboardLight & EFI_KEYBOARD_NUMLOCK) == EFI_KEYBOARD_NUMLOCK) {
1787 ConsoleIn->NumLock =
TRUE;
1790 if ((Ps2Policy->KeyboardLight & EFI_KEYBOARD_SCROLLLOCK) == EFI_KEYBOARD_SCROLLLOCK) {
1791 ConsoleIn->ScrollLock =
TRUE;
1799 if (EFI_ERROR (Status)) {
1800 KeyboardError (ConsoleIn, L
"Update keyboard status lights error!\n\r");
1810 if (mEnableMouseInterface) {
1814 Status1 =
KeyboardCommand (ConsoleIn, KEYBOARD_8042_COMMAND_ENABLE_MOUSE_INTERFACE);
1815 if (EFI_ERROR (Status1)) {
1816 KeyboardError (ConsoleIn, L
"8042 controller command write error!\n\r");
1817 return EFI_DEVICE_ERROR;
1821 if (!EFI_ERROR (Status)) {
1824 return EFI_DEVICE_ERROR;
1845 UINTN WaitForValueTimeOutBcakup;
1857 if (EFI_ERROR (Status)) {
1864 WaitForValueTimeOutBcakup = mWaitForValueTimeOut;
1865 mWaitForValueTimeOut = KEYBOARD_WAITFORVALUE_TIMEOUT;
1868 KEYBOARD_CMDECHO_ACK
1870 mWaitForValueTimeOut = WaitForValueTimeOutBcakup;
1872 if (EFI_ERROR (Status)) {
UINTN EFIAPI MicroSecondDelay(IN UINTN MicroSeconds)
BOOLEAN EFIAPI IsNull(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
LIST_ENTRY *EFIAPI GetNextNode(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
LIST_ENTRY *EFIAPI GetFirstNode(IN CONST LIST_ENTRY *List)
UINT8 EFIAPI IoWrite8(IN UINTN Port, IN UINT8 Value)
UINT8 EFIAPI IoRead8(IN UINTN Port)
EFI_RUNTIME_SERVICES * gRT
#define ASSERT_EFI_ERROR(StatusParameter)
#define CR(Record, TYPE, Field, TestSignature)
#define REPORT_STATUS_CODE_WITH_DEVICE_PATH(Type, Value, DevicePathParameter)
#define PcdGetBool(TokenName)
#define EFI_PROGRESS_CODE
#define EFI_P_KEYBOARD_PC_CLEAR_BUFFER
BOOLEAN EFIAPI CheckKeyboardConnect(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn)
VOID InitializeKeyState(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, OUT EFI_KEY_STATE *KeyState)
UINT8 KeyReadStatusRegister(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn)
EFI_STATUS KeyboardCommand(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN UINT8 Data)
VOID EFIAPI KeyboardTimerHandler(IN EFI_EVENT Event, IN VOID *Context)
VOID KeyboardError(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN CHAR16 *ErrMsg)
EFI_STATUS KeyboardWaitForValue(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN UINT8 Value)
UINT8 ScanCode
follows value defined in Scan Code Set1
EFI_STATUS KeyboardRead(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, OUT UINT8 *Data)
VOID PushScancodeBufTail(IN SCAN_CODE_QUEUE *Queue, IN UINT8 Scancode)
UINT8 KeyReadDataRegister(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn)
EFI_STATUS KeyboardWrite(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN UINT8 Data)
EFI_STATUS UpdateStatusLights(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn)
UINTN GetScancodeBufCount(IN SCAN_CODE_QUEUE *Queue)
EFI_STATUS PopScancodeBufHead(IN SCAN_CODE_QUEUE *Queue, IN UINTN Count, OUT UINT8 *Buf OPTIONAL)
EFI_STATUS GetScancodeBufHead(IN SCAN_CODE_QUEUE *Queue, IN UINTN Count, OUT UINT8 *Buf)
VOID KeyWriteDataRegister(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN UINT8 Data)
EFI_STATUS InitKeyboard(IN OUT KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN BOOLEAN ExtendedVerification)
VOID KeyWriteCommandRegister(IN KEYBOARD_CONSOLE_IN_DEV *ConsoleIn, IN UINT8 Data)
VOID KeyGetchar(IN OUT KEYBOARD_CONSOLE_IN_DEV *ConsoleIn)
VOID PushEfikeyBufTail(IN EFI_KEY_QUEUE *Queue, IN EFI_KEY_DATA *KeyData)
#define KEYBOARD_STATUS_REGISTER_TRANSMIT_TIMEOUT
0 - Transmit is complete without timeout; 1 - Transmit is timeout without complete
#define KEYBOARD_STATUS_REGISTER_HAS_OUTPUT_DATA
0 - Output register has no data; 1 - Output register has data
#define KEYBOARD_STATUS_REGISTER_SYSTEM_FLAG
Set to 0 after power on reset.
BOOLEAN IsKeyRegistered(IN EFI_KEY_DATA *RegsiteredData, IN EFI_KEY_DATA *InputData)