]> git.proxmox.com Git - mirror_edk2.git/blobdiff - IntelFrameworkModulePkg/Csm/BiosThunk/KeyboardDxe/BiosKeyboard.c
IntelFrameworkModulePkg/KeyboardDxe: Use macro to enable/disable page 0
[mirror_edk2.git] / IntelFrameworkModulePkg / Csm / BiosThunk / KeyboardDxe / BiosKeyboard.c
index 06ef9d3345648e11824cbd2fc16ee18276b0f183..ec525891dc7a5659af89d1151a008ee1cc84fd4f 100644 (file)
@@ -1,7 +1,7 @@
 /** @file\r
   ConsoleOut Routines that speak VGA.\r
 \r
 /** @file\r
   ConsoleOut Routines that speak VGA.\r
 \r
-Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR>\r
+Copyright (c) 2006 - 2017, Intel Corporation. All rights reserved.<BR>\r
 \r
 This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
 \r
 This program and the accompanying materials\r
 are licensed and made available under the terms and conditions\r
@@ -272,6 +272,8 @@ BiosKeyboardDriverBindingStart (
   \r
   BiosKeyboardPrivate->Queue.Front                = 0;\r
   BiosKeyboardPrivate->Queue.Rear                 = 0;\r
   \r
   BiosKeyboardPrivate->Queue.Front                = 0;\r
   BiosKeyboardPrivate->Queue.Rear                 = 0;\r
+  BiosKeyboardPrivate->QueueForNotify.Front       = 0;\r
+  BiosKeyboardPrivate->QueueForNotify.Rear        = 0;\r
   BiosKeyboardPrivate->SimpleTextInputEx.Reset               = BiosKeyboardResetEx;\r
   BiosKeyboardPrivate->SimpleTextInputEx.ReadKeyStrokeEx     = BiosKeyboardReadKeyStrokeEx;\r
   BiosKeyboardPrivate->SimpleTextInputEx.SetState            = BiosKeyboardSetState;\r
   BiosKeyboardPrivate->SimpleTextInputEx.Reset               = BiosKeyboardResetEx;\r
   BiosKeyboardPrivate->SimpleTextInputEx.ReadKeyStrokeEx     = BiosKeyboardReadKeyStrokeEx;\r
   BiosKeyboardPrivate->SimpleTextInputEx.SetState            = BiosKeyboardSetState;\r
@@ -279,19 +281,12 @@ BiosKeyboardDriverBindingStart (
   BiosKeyboardPrivate->SimpleTextInputEx.UnregisterKeyNotify = BiosKeyboardUnregisterKeyNotify;    \r
   InitializeListHead (&BiosKeyboardPrivate->NotifyList);\r
 \r
   BiosKeyboardPrivate->SimpleTextInputEx.UnregisterKeyNotify = BiosKeyboardUnregisterKeyNotify;    \r
   InitializeListHead (&BiosKeyboardPrivate->NotifyList);\r
 \r
-  Status = gBS->HandleProtocol (\r
-                  Controller,\r
-                  &gEfiDevicePathProtocolGuid,\r
-                  (VOID **) &BiosKeyboardPrivate->DevicePath\r
-                  );\r
-\r
   //\r
   // Report that the keyboard is being enabled\r
   //\r
   //\r
   // Report that the keyboard is being enabled\r
   //\r
-  REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
+  REPORT_STATUS_CODE (\r
     EFI_PROGRESS_CODE,\r
     EFI_PROGRESS_CODE,\r
-    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_ENABLE,\r
-    BiosKeyboardPrivate->DevicePath\r
+    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_ENABLE\r
     );\r
 \r
   //\r
     );\r
 \r
   //\r
@@ -346,14 +341,26 @@ BiosKeyboardDriverBindingStart (
     StatusCode  = EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_CONTROLLER_ERROR;\r
     goto Done;\r
   }\r
     StatusCode  = EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_CONTROLLER_ERROR;\r
     goto Done;\r
   }\r
-  \r
+\r
+  Status = gBS->CreateEvent (\r
+                  EVT_NOTIFY_SIGNAL,\r
+                  TPL_CALLBACK,\r
+                  KeyNotifyProcessHandler,\r
+                  BiosKeyboardPrivate,\r
+                  &BiosKeyboardPrivate->KeyNotifyProcessEvent\r
+                  );\r
+  if (EFI_ERROR (Status)) {\r
+    Status      = EFI_OUT_OF_RESOURCES;\r
+    StatusCode  = EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_CONTROLLER_ERROR;\r
+    goto Done;\r
+  }\r
+\r
   //\r
   // Report a Progress Code for an attempt to detect the precense of the keyboard device in the system\r
   //\r
   //\r
   // Report a Progress Code for an attempt to detect the precense of the keyboard device in the system\r
   //\r
-  REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
+  REPORT_STATUS_CODE (\r
     EFI_PROGRESS_CODE,\r
     EFI_PROGRESS_CODE,\r
-    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_PRESENCE_DETECT,\r
-    BiosKeyboardPrivate->DevicePath\r
+    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_PRESENCE_DETECT\r
     );\r
 \r
   //\r
     );\r
 \r
   //\r
@@ -361,10 +368,10 @@ BiosKeyboardDriverBindingStart (
   //\r
   Status = BiosKeyboardPrivate->SimpleTextInputEx.Reset (\r
                                                     &BiosKeyboardPrivate->SimpleTextInputEx,\r
   //\r
   Status = BiosKeyboardPrivate->SimpleTextInputEx.Reset (\r
                                                     &BiosKeyboardPrivate->SimpleTextInputEx,\r
-                                                    FALSE\r
+                                                    FeaturePcdGet (PcdPs2KbdExtendedVerification)\r
                                                     );\r
                                                     );\r
-\r
   if (EFI_ERROR (Status)) {\r
   if (EFI_ERROR (Status)) {\r
+    DEBUG ((EFI_D_ERROR, "[KBD]Reset Failed. Status - %r\n", Status));  \r
     StatusCode = EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_NOT_DETECTED;\r
     goto Done;\r
   }\r
     StatusCode = EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_NOT_DETECTED;\r
     goto Done;\r
   }\r
@@ -411,7 +418,7 @@ BiosKeyboardDriverBindingStart (
     // Check bit 6 of Feature Byte 2.\r
     // If it is set, then Int 16 Func 09 is supported\r
     //\r
     // Check bit 6 of Feature Byte 2.\r
     // If it is set, then Int 16 Func 09 is supported\r
     //\r
-    if (*(UINT8 *)(UINTN) ((Regs.X.ES << 4) + Regs.X.BX + 0x06) & 0x40) {\r
+    if (*(UINT8 *) (((UINTN) Regs.X.ES << 4) + Regs.X.BX + 0x06) & 0x40) {\r
       //\r
       // Get Keyboard Functionality\r
       //\r
       //\r
       // Get Keyboard Functionality\r
       //\r
@@ -436,6 +443,7 @@ BiosKeyboardDriverBindingStart (
       }\r
     }\r
   }\r
       }\r
     }\r
   }\r
+  DEBUG ((EFI_D_INFO, "[KBD]Extended keystrokes supported by CSM16 - %02x\n", (UINTN)BiosKeyboardPrivate->ExtendedKeyboard));\r
   //\r
   // Install protocol interfaces for the keyboard device.\r
   //\r
   //\r
   // Install protocol interfaces for the keyboard device.\r
   //\r
@@ -453,10 +461,9 @@ Done:
     //\r
     // Report an Error Code for failing to start the keyboard device\r
     //\r
     //\r
     // Report an Error Code for failing to start the keyboard device\r
     //\r
-    REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
+    REPORT_STATUS_CODE (\r
       EFI_ERROR_CODE | EFI_ERROR_MINOR,\r
       EFI_ERROR_CODE | EFI_ERROR_MINOR,\r
-      StatusCode,\r
-      BiosKeyboardPrivate->DevicePath\r
+      StatusCode\r
       );\r
   }\r
 \r
       );\r
   }\r
 \r
@@ -470,6 +477,11 @@ Done:
       if ((BiosKeyboardPrivate->SimpleTextInputEx).WaitForKeyEx != NULL) {\r
         gBS->CloseEvent ((BiosKeyboardPrivate->SimpleTextInputEx).WaitForKeyEx);    \r
       }\r
       if ((BiosKeyboardPrivate->SimpleTextInputEx).WaitForKeyEx != NULL) {\r
         gBS->CloseEvent ((BiosKeyboardPrivate->SimpleTextInputEx).WaitForKeyEx);    \r
       }\r
+\r
+      if (BiosKeyboardPrivate->KeyNotifyProcessEvent != NULL) {\r
+        gBS->CloseEvent (BiosKeyboardPrivate->KeyNotifyProcessEvent);\r
+      }\r
+\r
       BiosKeyboardFreeNotifyList (&BiosKeyboardPrivate->NotifyList);\r
 \r
       if (BiosKeyboardPrivate->TimerEvent != NULL) {\r
       BiosKeyboardFreeNotifyList (&BiosKeyboardPrivate->NotifyList);\r
 \r
       if (BiosKeyboardPrivate->TimerEvent != NULL) {\r
@@ -574,6 +586,7 @@ BiosKeyboardDriverBindingStop (
   gBS->CloseEvent ((BiosKeyboardPrivate->SimpleTextIn).WaitForKey);\r
   gBS->CloseEvent (BiosKeyboardPrivate->TimerEvent);\r
   gBS->CloseEvent (BiosKeyboardPrivate->SimpleTextInputEx.WaitForKeyEx);\r
   gBS->CloseEvent ((BiosKeyboardPrivate->SimpleTextIn).WaitForKey);\r
   gBS->CloseEvent (BiosKeyboardPrivate->TimerEvent);\r
   gBS->CloseEvent (BiosKeyboardPrivate->SimpleTextInputEx.WaitForKeyEx);\r
+  gBS->CloseEvent (BiosKeyboardPrivate->KeyNotifyProcessEvent);\r
   BiosKeyboardFreeNotifyList (&BiosKeyboardPrivate->NotifyList);\r
 \r
   FreePool (BiosKeyboardPrivate);\r
   BiosKeyboardFreeNotifyList (&BiosKeyboardPrivate->NotifyList);\r
 \r
   FreePool (BiosKeyboardPrivate);\r
@@ -942,7 +955,7 @@ KeyboardReadKeyStrokeWorker (
   }\r
 \r
   //\r
   }\r
 \r
   //\r
-  // Use TimerEvent callback funciton to check whether there's any key pressed\r
+  // Use TimerEvent callback function to check whether there's any key pressed\r
   //\r
   \r
   //\r
   //\r
   \r
   //\r
@@ -986,7 +999,7 @@ KeyboardReadKeyStrokeWorker (
   @param  ExtendedVerification  Whether perform the extra validation of keyboard. True: perform; FALSE: skip.\r
 \r
   @retval EFI_SUCCESS           The command byte is written successfully.\r
   @param  ExtendedVerification  Whether perform the extra validation of keyboard. True: perform; FALSE: skip.\r
 \r
   @retval EFI_SUCCESS           The command byte is written successfully.\r
-  @retval EFI_DEVICE_ERROR      Errors occurred during reseting keyboard.\r
+  @retval EFI_DEVICE_ERROR      Errors occurred during resetting keyboard.\r
 \r
 **/\r
 EFI_STATUS\r
 \r
 **/\r
 EFI_STATUS\r
@@ -1010,19 +1023,17 @@ BiosKeyboardReset (
   // 1\r
   // Report reset progress code\r
   //\r
   // 1\r
   // Report reset progress code\r
   //\r
-  REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
+  REPORT_STATUS_CODE (\r
     EFI_PROGRESS_CODE,\r
     EFI_PROGRESS_CODE,\r
-    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_RESET,\r
-    BiosKeyboardPrivate->DevicePath\r
+    EFI_PERIPHERAL_KEYBOARD | EFI_P_PC_RESET\r
     );\r
 \r
   //\r
   // Report a Progress Code for clearing the keyboard buffer\r
   //\r
     );\r
 \r
   //\r
   // Report a Progress Code for clearing the keyboard buffer\r
   //\r
-  REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
+  REPORT_STATUS_CODE (\r
     EFI_PROGRESS_CODE,\r
     EFI_PROGRESS_CODE,\r
-    EFI_PERIPHERAL_KEYBOARD | EFI_P_KEYBOARD_PC_CLEAR_BUFFER,\r
-    BiosKeyboardPrivate->DevicePath\r
+    EFI_PERIPHERAL_KEYBOARD | EFI_P_KEYBOARD_PC_CLEAR_BUFFER\r
     );\r
 \r
   //\r
     );\r
 \r
   //\r
@@ -1047,96 +1058,96 @@ BiosKeyboardReset (
   // if not skip step 4&5 and jump to step 6 to selftest KBC and report this\r
   // else   go step 4\r
   //\r
   // if not skip step 4&5 and jump to step 6 to selftest KBC and report this\r
   // else   go step 4\r
   //\r
-  if ((KeyReadStatusRegister (BiosKeyboardPrivate) & KBC_STSREG_VIA64_SYSF) != 0) {\r
-    //\r
-    // 4\r
-    // CheckMouseStatus to decide enable it later or not\r
-    //\r
-    //\r
-    // Read the command byte of KBC\r
-    //\r
-    Status = KeyboardCommand (\r
-               BiosKeyboardPrivate,\r
-               KBC_CMDREG_VIA64_CMDBYTE_R\r
-               );\r
-\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
-    }\r
-\r
-    Status = KeyboardRead (\r
-               BiosKeyboardPrivate,\r
-               &CommandByte\r
-               );\r
-\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
-    }\r
-    //\r
-    // Check mouse enabled or not before\r
-    //\r
-    if ((CommandByte & KB_CMMBYTE_DISABLE_AUX) != 0) {\r
-      MouseEnable = FALSE;\r
+  if (!PcdGetBool (PcdFastPS2Detection)) {\r
+    if ((KeyReadStatusRegister (BiosKeyboardPrivate) & KBC_STSREG_VIA64_SYSF) != 0) {\r
+      //\r
+      // 4\r
+      // CheckMouseStatus to decide enable it later or not\r
+      //\r
+      //\r
+      // Read the command byte of KBC\r
+      //\r
+      Status = KeyboardCommand (\r
+                 BiosKeyboardPrivate,\r
+                 KBC_CMDREG_VIA64_CMDBYTE_R\r
+                 );\r
+      \r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
+      \r
+      Status = KeyboardRead (\r
+                 BiosKeyboardPrivate,\r
+                 &CommandByte\r
+                 );\r
+      \r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
+      //\r
+      // Check mouse enabled or not before\r
+      //\r
+      if ((CommandByte & KB_CMMBYTE_DISABLE_AUX) != 0) {\r
+        MouseEnable = FALSE;\r
+      } else {\r
+        MouseEnable = TRUE;\r
+      }\r
+      //\r
+      // 5\r
+      // disable mouse (via KBC) and Keyborad device\r
+      //\r
+      Status = KeyboardCommand (\r
+                 BiosKeyboardPrivate,\r
+                 KBC_CMDREG_VIA64_AUX_DISABLE\r
+                 );\r
+      \r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
+      \r
+      Status = KeyboardCommand (\r
+                 BiosKeyboardPrivate,\r
+                 KBC_CMDREG_VIA64_KB_DISABLE\r
+                 );\r
+      \r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
     } else {\r
     } else {\r
-      MouseEnable = TRUE;\r
-    }\r
-    //\r
-    // 5\r
-    // disable mouse (via KBC) and Keyborad device\r
-    //\r
-    Status = KeyboardCommand (\r
-               BiosKeyboardPrivate,\r
-               KBC_CMDREG_VIA64_AUX_DISABLE\r
-               );\r
-\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
-    }\r
-\r
-    Status = KeyboardCommand (\r
-               BiosKeyboardPrivate,\r
-               KBC_CMDREG_VIA64_KB_DISABLE\r
-               );\r
-\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
-    }\r
-\r
-  } else {\r
-    //\r
-    // 6\r
-    // KBC Self Test\r
-    //\r
-    //\r
-    // Report a Progress Code for performing a self test on the keyboard controller\r
-    //\r
-    REPORT_STATUS_CODE_WITH_DEVICE_PATH (\r
-      EFI_PROGRESS_CODE,\r
-      EFI_PERIPHERAL_KEYBOARD | EFI_P_KEYBOARD_PC_SELF_TEST,\r
-      BiosKeyboardPrivate->DevicePath\r
-      );\r
-\r
-    Status = KeyboardCommand (\r
-               BiosKeyboardPrivate,\r
-               KBC_CMDREG_VIA64_KBC_SLFTEST\r
-               );\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
-    }\r
-\r
-    Status = KeyboardWaitForValue (\r
-               BiosKeyboardPrivate,\r
-               KBC_CMDECHO_KBCSLFTEST_OK,\r
-               KEYBOARD_WAITFORVALUE_TIMEOUT\r
-               );\r
-    if (EFI_ERROR (Status)) {\r
-      Status    = EFI_DEVICE_ERROR;\r
-      goto Exit;\r
+      //\r
+      // 6\r
+      // KBC Self Test\r
+      //\r
+      //\r
+      // Report a Progress Code for performing a self test on the keyboard controller\r
+      //    \r
+      REPORT_STATUS_CODE (\r
+        EFI_PROGRESS_CODE,\r
+        EFI_PERIPHERAL_KEYBOARD | EFI_P_KEYBOARD_PC_SELF_TEST\r
+        );\r
+      \r
+      Status = KeyboardCommand (\r
+                 BiosKeyboardPrivate,\r
+                 KBC_CMDREG_VIA64_KBC_SLFTEST\r
+                 );\r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
+      \r
+      Status = KeyboardWaitForValue (\r
+                 BiosKeyboardPrivate,\r
+                 KBC_CMDECHO_KBCSLFTEST_OK,\r
+                 KEYBOARD_WAITFORVALUE_TIMEOUT\r
+                 );\r
+      if (EFI_ERROR (Status)) {\r
+        Status    = EFI_DEVICE_ERROR;\r
+        goto Exit;\r
+      }\r
     }\r
   }\r
   //\r
     }\r
   }\r
   //\r
@@ -1186,8 +1197,8 @@ BiosKeyboardReset (
              );\r
 \r
   //\r
              );\r
 \r
   //\r
-  // For reseting keyboard is not mandatory before booting OS and sometimes keyboard responses very slow,\r
-  // so we only do the real reseting for keyboard when user asks, and normally during booting an OS, it's skipped.\r
+  // For resetting keyboard is not mandatory before booting OS and sometimes keyboard responses very slow,\r
+  // so we only do the real resetting for keyboard when user asks, and normally during booting an OS, it's skipped.\r
   // Call CheckKeyboardConnect() to check whether keyboard is connected, if it is not connected,\r
   // Real reset will not do.\r
   //\r
   // Call CheckKeyboardConnect() to check whether keyboard is connected, if it is not connected,\r
   // Real reset will not do.\r
   //\r
@@ -1332,14 +1343,16 @@ BiosKeyboardReset (
   // Done for validating keyboard. Enable keyboard (via KBC)\r
   // and recover the command byte to proper value\r
   //\r
   // Done for validating keyboard. Enable keyboard (via KBC)\r
   // and recover the command byte to proper value\r
   //\r
-  Status = KeyboardCommand (\r
-             BiosKeyboardPrivate,\r
-             KBC_CMDREG_VIA64_KB_ENABLE\r
-             );\r
-\r
-  if (EFI_ERROR (Status)) {\r
-    Status    = EFI_DEVICE_ERROR;\r
-    goto Exit;\r
+  if (!PcdGetBool (PcdFastPS2Detection)) {\r
+    Status = KeyboardCommand (\r
+               BiosKeyboardPrivate,\r
+               KBC_CMDREG_VIA64_KB_ENABLE\r
+               );\r
+    \r
+    if (EFI_ERROR (Status)) {\r
+      Status    = EFI_DEVICE_ERROR;\r
+      goto Exit;\r
+    }\r
   }\r
 \r
   //\r
   }\r
 \r
   //\r
@@ -1397,6 +1410,17 @@ BiosKeyboardReadKeyStroke (
     return Status;\r
   }\r
 \r
     return Status;\r
   }\r
 \r
+  //\r
+  // Convert the Ctrl+[a-z] to Ctrl+[1-26]\r
+  //\r
+  if ((KeyData.KeyState.KeyShiftState & (EFI_LEFT_CONTROL_PRESSED | EFI_RIGHT_CONTROL_PRESSED)) != 0) {\r
+    if (KeyData.Key.UnicodeChar >= L'a' && KeyData.Key.UnicodeChar <= L'z') {\r
+      KeyData.Key.UnicodeChar = (CHAR16) (KeyData.Key.UnicodeChar - L'a' + 1);\r
+    } else if (KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') {\r
+      KeyData.Key.UnicodeChar = (CHAR16) (KeyData.Key.UnicodeChar - L'A' + 1);\r
+    }\r
+  }\r
+\r
   CopyMem (Key, &KeyData.Key, sizeof (EFI_INPUT_KEY));  \r
 \r
   return EFI_SUCCESS;\r
   CopyMem (Key, &KeyData.Key, sizeof (EFI_INPUT_KEY));  \r
 \r
   return EFI_SUCCESS;\r
@@ -1428,7 +1452,7 @@ BiosKeyboardWaitForKey (
   //\r
   gBS->Stall (1000);\r
   //\r
   //\r
   gBS->Stall (1000);\r
   //\r
-  // Use TimerEvent callback funciton to check whether there's any key pressed\r
+  // Use TimerEvent callback function to check whether there's any key pressed\r
   //\r
   BiosKeyboardTimerHandler (NULL, BIOS_KEYBOARD_DEV_FROM_THIS (Context));\r
 \r
   //\r
   BiosKeyboardTimerHandler (NULL, BIOS_KEYBOARD_DEV_FROM_THIS (Context));\r
 \r
@@ -1674,25 +1698,38 @@ CheckKeyboardConnect (
   // enable keyboard itself and wait for its ack\r
   // If can't receive ack, Keyboard should not be connected.\r
   //\r
   // enable keyboard itself and wait for its ack\r
   // If can't receive ack, Keyboard should not be connected.\r
   //\r
-  Status = KeyboardWrite (\r
-             BiosKeyboardPrivate,\r
-             KBC_INPBUF_VIA60_KBEN\r
-             );\r
-  if (EFI_ERROR (Status)) {\r
-    return FALSE;\r
-  }\r
+  if (!PcdGetBool (PcdFastPS2Detection)) {\r
+    Status = KeyboardWrite (\r
+               BiosKeyboardPrivate,\r
+               KBC_INPBUF_VIA60_KBEN\r
+               );\r
+    if (EFI_ERROR (Status)) {\r
+      DEBUG ((EFI_D_ERROR, "[KBD]CheckKeyboardConnect - Keyboard enable failed!\n"));\r
+      REPORT_STATUS_CODE (\r
+        EFI_ERROR_CODE | EFI_ERROR_MINOR,\r
+        EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_CONTROLLER_ERROR\r
+        );\r
+      return FALSE;\r
+    }\r
 \r
 \r
-  Status = KeyboardWaitForValue (\r
-             BiosKeyboardPrivate,\r
-             KBC_CMDECHO_ACK,\r
-             KEYBOARD_WAITFORVALUE_TIMEOUT\r
-             );\r
+    Status = KeyboardWaitForValue (\r
+               BiosKeyboardPrivate,\r
+               KBC_CMDECHO_ACK,\r
+               KEYBOARD_WAITFORVALUE_TIMEOUT\r
+               );\r
 \r
 \r
-  if (EFI_ERROR (Status)) {\r
-    return FALSE;\r
+    if (EFI_ERROR (Status)) {\r
+      DEBUG ((EFI_D_ERROR, "[KBD]CheckKeyboardConnect - Timeout!\n"));\r
+      REPORT_STATUS_CODE (\r
+        EFI_ERROR_CODE | EFI_ERROR_MINOR,\r
+        EFI_PERIPHERAL_KEYBOARD | EFI_P_EC_CONTROLLER_ERROR\r
+        );\r
+      return FALSE;\r
+    }\r
+    return TRUE;\r
+  } else {\r
+    return TRUE;\r
   }\r
   }\r
-\r
-  return TRUE;\r
 }\r
 \r
 /**\r
 }\r
 \r
 /**\r
@@ -1763,6 +1800,13 @@ BiosKeyboardTimerHandler (
 \r
   KeyData.Key.ScanCode            = (UINT16) Regs.H.AH;\r
   KeyData.Key.UnicodeChar         = (UINT16) Regs.H.AL;\r
 \r
   KeyData.Key.ScanCode            = (UINT16) Regs.H.AH;\r
   KeyData.Key.UnicodeChar         = (UINT16) Regs.H.AL;\r
+  DEBUG ((\r
+    EFI_D_INFO,\r
+    "[KBD]INT16 returns EFI_INPUT_KEY.ScanCode - %x, EFI_INPUT_KEY.UnicodeChar - %x\n",\r
+    KeyData.Key.ScanCode,\r
+    KeyData.Key.UnicodeChar\r
+    ));\r
+  \r
   KeyData.KeyState.KeyShiftState  = EFI_SHIFT_STATE_VALID;\r
   KeyData.KeyState.KeyToggleState = EFI_TOGGLE_STATE_VALID;\r
   //\r
   KeyData.KeyState.KeyShiftState  = EFI_SHIFT_STATE_VALID;\r
   KeyData.KeyState.KeyToggleState = EFI_TOGGLE_STATE_VALID;\r
   //\r
@@ -1772,7 +1816,7 @@ BiosKeyboardTimerHandler (
   // will be disabled after the thunk call finish, which means if user crazy input during int 9 being disabled, some keystrokes will be lost when \r
   // KB device own hardware buffer overflows. And if the lost keystroke code is CTRL or ALT or SHIFT release code, these function key flags bit \r
   // in BDA will not be updated. So the Int 16 will believe the CTRL or ALT or SHIFT is still pressed, and Int 16 will translate later scancode \r
   // will be disabled after the thunk call finish, which means if user crazy input during int 9 being disabled, some keystrokes will be lost when \r
   // KB device own hardware buffer overflows. And if the lost keystroke code is CTRL or ALT or SHIFT release code, these function key flags bit \r
   // in BDA will not be updated. So the Int 16 will believe the CTRL or ALT or SHIFT is still pressed, and Int 16 will translate later scancode \r
-  // to wrong ASCII code. We can increase the Thunk frequence to let Int 9 response in time, but this way will much hurt other dirvers \r
+  // to wrong ASCII code. We can increase the Thunk frequence to let Int 9 response in time, but this way will much hurt other drivers\r
   // performance, like USB.\r
   //\r
   // 1. If CTRL or ALT release code is missed,  all later input keys will be translated to wrong ASCII codes which the Tiano cannot support. In \r
   // performance, like USB.\r
   //\r
   // 1. If CTRL or ALT release code is missed,  all later input keys will be translated to wrong ASCII codes which the Tiano cannot support. In \r
@@ -1798,8 +1842,44 @@ BiosKeyboardTimerHandler (
   //\r
   // Clear the CTRL and ALT BDA flag\r
   //\r
   //\r
   // Clear the CTRL and ALT BDA flag\r
   //\r
-  KbFlag1 = *((UINT8 *) (UINTN) 0x417);  // read the STATUS FLAGS 1\r
-  KbFlag2 = *((UINT8 *) (UINTN) 0x418); // read STATUS FLAGS 2\r
+  ACCESS_PAGE0_CODE (\r
+    KbFlag1 = *((UINT8 *) (UINTN) 0x417); // read the STATUS FLAGS 1\r
+    KbFlag2 = *((UINT8 *) (UINTN) 0x418); // read STATUS FLAGS 2\r
+  );\r
+\r
+  DEBUG_CODE (\r
+    {\r
+      if ((KbFlag1 & KB_CAPS_LOCK_BIT) == KB_CAPS_LOCK_BIT) {\r
+        DEBUG ((EFI_D_INFO, "[KBD]Caps Lock Key is pressed.\n"));\r
+      }\r
+      if ((KbFlag1 & KB_NUM_LOCK_BIT) == KB_NUM_LOCK_BIT) {\r
+        DEBUG ((EFI_D_INFO, "[KBD]Num Lock Key is pressed.\n"));\r
+      }\r
+      if ((KbFlag1 & KB_SCROLL_LOCK_BIT) == KB_SCROLL_LOCK_BIT) {\r
+        DEBUG ((EFI_D_INFO, "[KBD]Scroll Lock Key is pressed.\n"));\r
+      } \r
+      if ((KbFlag1 & KB_ALT_PRESSED) == KB_ALT_PRESSED) {\r
+        if ((KbFlag2 & KB_LEFT_ALT_PRESSED) == KB_LEFT_ALT_PRESSED) {\r
+          DEBUG ((EFI_D_INFO, "[KBD]Left Alt Key is pressed.\n"));\r
+        } else {\r
+          DEBUG ((EFI_D_INFO, "[KBD]Right Alt Key is pressed.\n"));\r
+        }\r
+      }  \r
+      if ((KbFlag1 & KB_CTRL_PRESSED) == KB_CTRL_PRESSED) {\r
+        if ((KbFlag2 & KB_LEFT_CTRL_PRESSED) == KB_LEFT_CTRL_PRESSED) {\r
+          DEBUG ((EFI_D_INFO, "[KBD]Left Ctrl Key is pressed.\n"));\r
+        } else {\r
+          DEBUG ((EFI_D_INFO, "[KBD]Right Ctrl Key is pressed.\n"));\r
+        }\r
+      }  \r
+      if ((KbFlag1 & KB_LEFT_SHIFT_PRESSED) == KB_LEFT_SHIFT_PRESSED) {\r
+        DEBUG ((EFI_D_INFO, "[KBD]Left Shift Key is pressed.\n"));\r
+      }\r
+      if ((KbFlag1 & KB_RIGHT_SHIFT_PRESSED) == KB_RIGHT_SHIFT_PRESSED) {\r
+        DEBUG ((EFI_D_INFO, "[KBD]Right Shift Key is pressed.\n"));\r
+      }\r
+    }\r
+  );\r
 \r
   //\r
   // Record toggle state\r
 \r
   //\r
   // Record toggle state\r
@@ -1833,11 +1913,12 @@ BiosKeyboardTimerHandler (
   //\r
   // Clear left alt and left ctrl BDA flag\r
   //\r
   //\r
   // Clear left alt and left ctrl BDA flag\r
   //\r
-  KbFlag2 &= ~(KB_LEFT_ALT_PRESSED | KB_LEFT_CTRL_PRESSED);\r
-  *((UINT8 *) (UINTN) 0x418) = KbFlag2;\r
-  KbFlag1 &= ~0x0C;                      \r
-  *((UINT8 *) (UINTN) 0x417) = KbFlag1; \r
-\r
+  ACCESS_PAGE0_CODE (\r
+    KbFlag2 &= ~(KB_LEFT_ALT_PRESSED | KB_LEFT_CTRL_PRESSED);\r
+    *((UINT8 *) (UINTN) 0x418) = KbFlag2;\r
+    KbFlag1 &= ~0x0C;\r
+    *((UINT8 *) (UINTN) 0x417) = KbFlag1;\r
+  );\r
   \r
   //\r
   // Output EFI input key and shift/toggle state\r
   \r
   //\r
   // Output EFI input key and shift/toggle state\r
@@ -1864,6 +1945,13 @@ BiosKeyboardTimerHandler (
     }\r
   }\r
 \r
     }\r
   }\r
 \r
+  DEBUG ((\r
+    EFI_D_INFO,\r
+    "[KBD]Convert to EFI Scan Code, EFI_INPUT_KEY.ScanCode - %x, EFI_INPUT_KEY.UnicodeChar - %x\n",\r
+    KeyData.Key.ScanCode,\r
+    KeyData.Key.UnicodeChar\r
+    ));\r
+\r
   //\r
   // Need not return associated shift state if a class of printable characters that\r
   // are normally adjusted by shift modifiers.\r
   //\r
   // Need not return associated shift state if a class of printable characters that\r
   // are normally adjusted by shift modifiers.\r
@@ -1872,11 +1960,12 @@ BiosKeyboardTimerHandler (
   if ((KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') ||\r
       (KeyData.Key.UnicodeChar >= L'a' && KeyData.Key.UnicodeChar <= L'z')\r
      ) {\r
   if ((KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') ||\r
       (KeyData.Key.UnicodeChar >= L'a' && KeyData.Key.UnicodeChar <= L'z')\r
      ) {\r
+    DEBUG ((EFI_D_INFO, "[KBD]Shift key with a~z are pressed, remove shift state in EFI_KEY_STATE.\n"));\r
     KeyData.KeyState.KeyShiftState &= ~(EFI_LEFT_SHIFT_PRESSED | EFI_RIGHT_SHIFT_PRESSED);\r
   }\r
 \r
   //\r
     KeyData.KeyState.KeyShiftState &= ~(EFI_LEFT_SHIFT_PRESSED | EFI_RIGHT_SHIFT_PRESSED);\r
   }\r
 \r
   //\r
-  // Invoke notification functions if exist\r
+  // Signal KeyNotify process event if this key pressed matches any key registered.\r
   //\r
   for (Link = BiosKeyboardPrivate->NotifyList.ForwardLink; Link != &BiosKeyboardPrivate->NotifyList; Link = Link->ForwardLink) {\r
     CurrentNotify = CR (\r
   //\r
   for (Link = BiosKeyboardPrivate->NotifyList.ForwardLink; Link != &BiosKeyboardPrivate->NotifyList; Link = Link->ForwardLink) {\r
     CurrentNotify = CR (\r
@@ -1885,21 +1974,17 @@ BiosKeyboardTimerHandler (
                       NotifyEntry, \r
                       BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE\r
                       );\r
                       NotifyEntry, \r
                       BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE\r
                       );\r
-    if (IsKeyRegistered (&CurrentNotify->KeyData, &KeyData)) { \r
-      CurrentNotify->KeyNotificationFn (&KeyData);\r
+    if (IsKeyRegistered (&CurrentNotify->KeyData, &KeyData)) {\r
+      //\r
+      // The key notification function needs to run at TPL_CALLBACK\r
+      // while current TPL is TPL_NOTIFY. It will be invoked in\r
+      // KeyNotifyProcessHandler() which runs at TPL_CALLBACK.\r
+      //\r
+      Enqueue (&BiosKeyboardPrivate->QueueForNotify, &KeyData);\r
+      gBS->SignalEvent (BiosKeyboardPrivate->KeyNotifyProcessEvent);\r
     }\r
   }\r
 \r
     }\r
   }\r
 \r
-  //\r
-  // Convert the Ctrl+[a-z] to Ctrl+[1-26]\r
-  //\r
-  if ((KeyData.KeyState.KeyShiftState & (EFI_LEFT_CONTROL_PRESSED | EFI_RIGHT_CONTROL_PRESSED)) != 0) {\r
-    if (KeyData.Key.UnicodeChar >= L'a' && KeyData.Key.UnicodeChar <= L'z') {\r
-      KeyData.Key.UnicodeChar = (UINT16) (KeyData.Key.UnicodeChar - L'a' + 1);\r
-    } else if (KeyData.Key.UnicodeChar >= L'A' && KeyData.Key.UnicodeChar <= L'Z') {\r
-      KeyData.Key.UnicodeChar = (UINT16) (KeyData.Key.UnicodeChar - L'A' + 1);\r
-    }\r
-  }\r
   Enqueue (&BiosKeyboardPrivate->Queue, &KeyData);\r
   //\r
   // Leave critical section and return\r
   Enqueue (&BiosKeyboardPrivate->Queue, &KeyData);\r
   //\r
   // Leave critical section and return\r
@@ -1909,6 +1994,55 @@ BiosKeyboardTimerHandler (
   return ;  \r
 }\r
 \r
   return ;  \r
 }\r
 \r
+/**\r
+  Process key notify.\r
+\r
+  @param  Event                 Indicates the event that invoke this function.\r
+  @param  Context               Indicates the calling context.\r
+**/\r
+VOID\r
+EFIAPI\r
+KeyNotifyProcessHandler (\r
+  IN  EFI_EVENT                 Event,\r
+  IN  VOID                      *Context\r
+  )\r
+{\r
+  EFI_STATUS                            Status;\r
+  BIOS_KEYBOARD_DEV                     *BiosKeyboardPrivate;\r
+  EFI_KEY_DATA                          KeyData;\r
+  LIST_ENTRY                            *Link;\r
+  LIST_ENTRY                            *NotifyList;\r
+  BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY    *CurrentNotify;\r
+  EFI_TPL                               OldTpl;\r
+\r
+  BiosKeyboardPrivate = (BIOS_KEYBOARD_DEV *) Context;\r
+\r
+  //\r
+  // Invoke notification functions.\r
+  //\r
+  NotifyList = &BiosKeyboardPrivate->NotifyList;\r
+  while (TRUE) {\r
+    //\r
+    // Enter critical section\r
+    //  \r
+    OldTpl = gBS->RaiseTPL (TPL_NOTIFY);\r
+    Status = Dequeue (&BiosKeyboardPrivate->QueueForNotify, &KeyData);\r
+    //\r
+    // Leave critical section\r
+    //\r
+    gBS->RestoreTPL (OldTpl);\r
+    if (EFI_ERROR (Status)) {\r
+      break;\r
+    }\r
+    for (Link = GetFirstNode (NotifyList); !IsNull (NotifyList, Link); Link = GetNextNode (NotifyList, Link)) {\r
+      CurrentNotify = CR (Link, BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY, NotifyEntry, BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE);\r
+      if (IsKeyRegistered (&CurrentNotify->KeyData, &KeyData)) {\r
+        CurrentNotify->KeyNotificationFn (&KeyData);\r
+      }\r
+    }\r
+  }\r
+}\r
+\r
 /**\r
   Free keyboard notify list.\r
 \r
 /**\r
   Free keyboard notify list.\r
 \r
@@ -2109,7 +2243,12 @@ BiosKeyboardSetState (
     return EFI_INVALID_PARAMETER;\r
   }\r
 \r
     return EFI_INVALID_PARAMETER;\r
   }\r
 \r
-  if ((*KeyToggleState & EFI_TOGGLE_STATE_VALID) != EFI_TOGGLE_STATE_VALID) {\r
+  //\r
+  // Thunk keyboard driver doesn't support partial keystroke.\r
+  //\r
+  if ((*KeyToggleState & EFI_TOGGLE_STATE_VALID) != EFI_TOGGLE_STATE_VALID ||\r
+      (*KeyToggleState & EFI_KEY_STATE_EXPOSED) == EFI_KEY_STATE_EXPOSED\r
+      ) {\r
     return EFI_UNSUPPORTED;\r
   }\r
 \r
     return EFI_UNSUPPORTED;\r
   }\r
 \r
@@ -2142,15 +2281,18 @@ BiosKeyboardSetState (
 \r
   Status = KeyboardWrite (BiosKeyboardPrivate, 0xed);\r
   if (EFI_ERROR (Status)) {\r
 \r
   Status = KeyboardWrite (BiosKeyboardPrivate, 0xed);\r
   if (EFI_ERROR (Status)) {\r
-    return EFI_DEVICE_ERROR;\r
+    Status = EFI_DEVICE_ERROR;\r
+    goto Exit;\r
   }  \r
   Status = KeyboardWaitForValue (BiosKeyboardPrivate, 0xfa, KEYBOARD_WAITFORVALUE_TIMEOUT);\r
   if (EFI_ERROR (Status)) {\r
   }  \r
   Status = KeyboardWaitForValue (BiosKeyboardPrivate, 0xfa, KEYBOARD_WAITFORVALUE_TIMEOUT);\r
   if (EFI_ERROR (Status)) {\r
-    return EFI_DEVICE_ERROR;\r
+    Status = EFI_DEVICE_ERROR;\r
+    goto Exit;\r
   }\r
   Status = KeyboardWrite (BiosKeyboardPrivate, Command);\r
   if (EFI_ERROR (Status)) {\r
   }\r
   Status = KeyboardWrite (BiosKeyboardPrivate, Command);\r
   if (EFI_ERROR (Status)) {\r
-    return EFI_DEVICE_ERROR;\r
+    Status = EFI_DEVICE_ERROR;\r
+    goto Exit;\r
   }  \r
   //\r
   // Call Legacy BIOS Protocol to set whatever is necessary\r
   }  \r
   //\r
   // Call Legacy BIOS Protocol to set whatever is necessary\r
@@ -2159,6 +2301,7 @@ BiosKeyboardSetState (
 \r
   Status = EFI_SUCCESS;\r
 \r
 \r
   Status = EFI_SUCCESS;\r
 \r
+Exit:\r
   //\r
   // Leave critical section and return\r
   //\r
   //\r
   // Leave critical section and return\r
   //\r
@@ -2173,24 +2316,27 @@ BiosKeyboardSetState (
 \r
   @param  This                    Protocol instance pointer.\r
   @param  KeyData                 A pointer to a buffer that is filled in with the keystroke \r
 \r
   @param  This                    Protocol instance pointer.\r
   @param  KeyData                 A pointer to a buffer that is filled in with the keystroke \r
-                                  information data for the key that was pressed.\r
+                                  information data for the key that was pressed. If KeyData.Key,\r
+                                  KeyData.KeyState.KeyToggleState and KeyData.KeyState.KeyShiftState\r
+                                  are 0, then any incomplete keystroke will trigger a notification of\r
+                                  the KeyNotificationFunction.\r
   @param  KeyNotificationFunction Points to the function to be called when the key \r
   @param  KeyNotificationFunction Points to the function to be called when the key \r
-                                  sequence is typed specified by KeyData.                        \r
-  @param  NotifyHandle            Points to the unique handle assigned to the registered notification.                          \r
+                                  sequence is typed specified by KeyData. This notification function\r
+                                  should be called at <=TPL_CALLBACK.\r
+  @param  NotifyHandle            Points to the unique handle assigned to the registered notification.\r
 \r
 \r
-  \r
   @retval EFI_SUCCESS             The notification function was registered successfully.\r
   @retval EFI_OUT_OF_RESOURCES    Unable to allocate resources for necesssary data structures.\r
   @retval EFI_INVALID_PARAMETER   KeyData or NotifyHandle is NULL.\r
   @retval EFI_SUCCESS             The notification function was registered successfully.\r
   @retval EFI_OUT_OF_RESOURCES    Unable to allocate resources for necesssary data structures.\r
   @retval EFI_INVALID_PARAMETER   KeyData or NotifyHandle is NULL.\r
-                                                  \r
-**/   \r
+\r
+**/\r
 EFI_STATUS\r
 EFIAPI\r
 BiosKeyboardRegisterKeyNotify (\r
   IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL  *This,\r
   IN EFI_KEY_DATA                       *KeyData,\r
   IN EFI_KEY_NOTIFY_FUNCTION            KeyNotificationFunction,\r
 EFI_STATUS\r
 EFIAPI\r
 BiosKeyboardRegisterKeyNotify (\r
   IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL  *This,\r
   IN EFI_KEY_DATA                       *KeyData,\r
   IN EFI_KEY_NOTIFY_FUNCTION            KeyNotificationFunction,\r
-  OUT EFI_HANDLE                        *NotifyHandle\r
+  OUT VOID                              **NotifyHandle\r
   )\r
 {\r
   EFI_STATUS                            Status;\r
   )\r
 {\r
   EFI_STATUS                            Status;\r
@@ -2223,7 +2369,7 @@ BiosKeyboardRegisterKeyNotify (
                       );\r
     if (IsKeyRegistered (&CurrentNotify->KeyData, KeyData)) { \r
       if (CurrentNotify->KeyNotificationFn == KeyNotificationFunction) {\r
                       );\r
     if (IsKeyRegistered (&CurrentNotify->KeyData, KeyData)) { \r
       if (CurrentNotify->KeyNotificationFn == KeyNotificationFunction) {\r
-        *NotifyHandle = CurrentNotify->NotifyHandle;        \r
+        *NotifyHandle = CurrentNotify;\r
         Status = EFI_SUCCESS;\r
         goto Exit;\r
       }\r
         Status = EFI_SUCCESS;\r
         goto Exit;\r
       }\r
@@ -2242,11 +2388,10 @@ BiosKeyboardRegisterKeyNotify (
 \r
   NewNotify->Signature         = BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE;\r
   NewNotify->KeyNotificationFn = KeyNotificationFunction;\r
 \r
   NewNotify->Signature         = BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE;\r
   NewNotify->KeyNotificationFn = KeyNotificationFunction;\r
-  NewNotify->NotifyHandle      = (EFI_HANDLE) NewNotify;\r
   CopyMem (&NewNotify->KeyData, KeyData, sizeof (EFI_KEY_DATA));\r
   InsertTailList (&BiosKeyboardPrivate->NotifyList, &NewNotify->NotifyEntry);\r
 \r
   CopyMem (&NewNotify->KeyData, KeyData, sizeof (EFI_KEY_DATA));\r
   InsertTailList (&BiosKeyboardPrivate->NotifyList, &NewNotify->NotifyEntry);\r
 \r
-  *NotifyHandle                = NewNotify->NotifyHandle;  \r
+  *NotifyHandle                = NewNotify;\r
   Status                       = EFI_SUCCESS;\r
   \r
 Exit:\r
   Status                       = EFI_SUCCESS;\r
   \r
 Exit:\r
@@ -2271,7 +2416,7 @@ EFI_STATUS
 EFIAPI\r
 BiosKeyboardUnregisterKeyNotify (\r
   IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL  *This,\r
 EFIAPI\r
 BiosKeyboardUnregisterKeyNotify (\r
   IN EFI_SIMPLE_TEXT_INPUT_EX_PROTOCOL  *This,\r
-  IN EFI_HANDLE                         NotificationHandle\r
+  IN VOID                               *NotificationHandle\r
   )\r
 {\r
   EFI_STATUS                            Status;\r
   )\r
 {\r
   EFI_STATUS                            Status;\r
@@ -2296,7 +2441,7 @@ BiosKeyboardUnregisterKeyNotify (
   //\r
   // Enter critical section\r
   //\r
   //\r
   // Enter critical section\r
   //\r
-  OldTpl = gBS->RaiseTPL (TPL_NOTIFY);  \r
+  OldTpl = gBS->RaiseTPL (TPL_NOTIFY);\r
 \r
   for (Link = BiosKeyboardPrivate->NotifyList.ForwardLink; Link != &BiosKeyboardPrivate->NotifyList; Link = Link->ForwardLink) {\r
     CurrentNotify = CR (\r
 \r
   for (Link = BiosKeyboardPrivate->NotifyList.ForwardLink; Link != &BiosKeyboardPrivate->NotifyList; Link = Link->ForwardLink) {\r
     CurrentNotify = CR (\r
@@ -2305,7 +2450,7 @@ BiosKeyboardUnregisterKeyNotify (
                       NotifyEntry, \r
                       BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE\r
                       );    \r
                       NotifyEntry, \r
                       BIOS_KEYBOARD_CONSOLE_IN_EX_NOTIFY_SIGNATURE\r
                       );    \r
-    if (CurrentNotify->NotifyHandle == NotificationHandle) {\r
+    if (CurrentNotify == NotificationHandle) {\r
       //\r
       // Remove the notification function from NotifyList and free resources\r
       //\r
       //\r
       // Remove the notification function from NotifyList and free resources\r
       //\r