]> git.proxmox.com Git - mirror_edk2.git/blobdiff - MdeModulePkg/Universal/Console/TerminalDxe/Terminal.c
MdeModulePkg TerminalDxe: Execute key notify func at TPL_CALLBACK
[mirror_edk2.git] / MdeModulePkg / Universal / Console / TerminalDxe / Terminal.c
index 008e746b334d20708d7a9bf5b98ee9937a2047eb..a209bf3cacf8e729432c9677af42f5030ee5de94 100644 (file)
@@ -2,7 +2,7 @@
   Produces Simple Text Input Protocol, Simple Text Input Extended Protocol and\r
   Simple Text Output Protocol upon Serial IO Protocol.\r
 \r
-Copyright (c) 2006 - 2012, Intel Corporation. All rights reserved.<BR>\r
+Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>\r
 This program and the accompanying materials\r
 are licensed and made available under the terms and conditions of the BSD License\r
 which accompanies this distribution.  The full text of the license may be found at\r
@@ -33,7 +33,8 @@ EFI_GUID  *gTerminalType[] = {
   &gEfiPcAnsiGuid,\r
   &gEfiVT100Guid,\r
   &gEfiVT100PlusGuid,\r
-  &gEfiVTUTF8Guid\r
+  &gEfiVTUTF8Guid,\r
+  &gEfiTtyTermGuid\r
 };\r
 \r
 \r
@@ -74,12 +75,19 @@ TERMINAL_DEV  mTerminalDevTemplate = {
   NULL, // RawFifo\r
   NULL, // UnicodeFiFo\r
   NULL, // EfiKeyFiFo\r
+  NULL, // EfiKeyFiFoForNotify\r
 \r
   NULL, // ControllerNameTable\r
   NULL, // TimerEvent\r
   NULL, // TwoSecondTimeOut\r
   INPUT_STATE_DEFAULT,\r
   RESET_STATE_DEFAULT,\r
+  {\r
+      0,\r
+      0,\r
+      0\r
+  },\r
+  0,\r
   FALSE,\r
   {   // SimpleTextInputEx\r
     TerminalConInResetEx,\r
@@ -92,7 +100,8 @@ TERMINAL_DEV  mTerminalDevTemplate = {
   {   // NotifyList\r
     NULL,\r
     NULL,\r
-  }\r
+  },\r
+  NULL // KeyNotifyProcessEvent\r
 };\r
 \r
 TERMINAL_CONSOLE_MODE_DATA mTerminalConsoleModeData[] = {\r
@@ -152,12 +161,13 @@ TerminalDriverBindingSupported (
 \r
       }\r
       //\r
-      // only supports PC ANSI, VT100, VT100+ and VT-UTF8 terminal types\r
+      // only supports PC ANSI, VT100, VT100+, VT-UTF8, and TtyTerm terminal types\r
       //\r
       if (!CompareGuid (&Node->Guid, &gEfiPcAnsiGuid) &&\r
           !CompareGuid (&Node->Guid, &gEfiVT100Guid) &&\r
           !CompareGuid (&Node->Guid, &gEfiVT100PlusGuid) &&\r
-          !CompareGuid (&Node->Guid, &gEfiVTUTF8Guid)) {\r
+          !CompareGuid (&Node->Guid, &gEfiVTUTF8Guid) &&\r
+          !CompareGuid (&Node->Guid, &gEfiTtyTermGuid)) {\r
 \r
         return EFI_UNSUPPORTED;\r
       }\r
@@ -250,14 +260,13 @@ BuildTerminalDevpath  (
   EFI_STATUS                        Status;\r
 \r
   TerminalDevicePath = NULL;\r
-  TerminalType = PCANSITYPE;\r
 \r
   //\r
   // Use the RemainingDevicePath to determine the terminal type\r
   //\r
   Node = (VENDOR_DEVICE_PATH *) RemainingDevicePath;\r
   if (Node == NULL) {\r
-    TerminalType = PCANSITYPE;\r
+    TerminalType = PcdGet8 (PcdDefaultTerminalType);\r
 \r
   } else if (CompareGuid (&Node->Guid, &gEfiPcAnsiGuid)) {\r
 \r
@@ -275,6 +284,10 @@ BuildTerminalDevpath  (
 \r
     TerminalType = VTUTF8TYPE;\r
 \r
+  } else if (CompareGuid (&Node->Guid, &gEfiTtyTermGuid)) {\r
+\r
+    TerminalType = TTYTERMTYPE;\r
+\r
   } else {\r
     return NULL;\r
   }\r
@@ -358,7 +371,7 @@ IsTerminalInConsoleVariable (
   //\r
   // Get global variable and its size according to the name given.\r
   //\r
-  GetEfiGlobalVariable2 (VariableName, &Variable, NULL);\r
+  GetEfiGlobalVariable2 (VariableName, (VOID**)&Variable, NULL);\r
   if (Variable == NULL) {\r
     return FALSE;\r
   }\r
@@ -533,7 +546,6 @@ TerminalDriverBindingStart (
   EFI_SERIAL_IO_PROTOCOL              *SerialIo;\r
   EFI_DEVICE_PATH_PROTOCOL            *ParentDevicePath;\r
   VENDOR_DEVICE_PATH                  *Node;\r
-  VENDOR_DEVICE_PATH                  *DefaultNode;\r
   EFI_SERIAL_IO_MODE                  *Mode;\r
   UINTN                               SerialInTimeOut;\r
   TERMINAL_DEV                        *TerminalDevice;\r
@@ -553,10 +565,9 @@ TerminalDriverBindingStart (
   UINTN                               ModeCount;\r
 \r
   TerminalDevice     = NULL;\r
-  DefaultNode        = NULL;\r
-  ConInSelected       = FALSE;\r
-  ConOutSelected      = FALSE;\r
-  NullRemaining      = TRUE;\r
+  ConInSelected      = FALSE;\r
+  ConOutSelected     = FALSE;\r
+  NullRemaining      = FALSE;\r
   SimTxtInInstalled  = FALSE;\r
   SimTxtOutInstalled = FALSE;\r
   FirstEnter         = FALSE;\r
@@ -669,7 +680,7 @@ TerminalDriverBindingStart (
   //\r
   if (FirstEnter) {\r
     //\r
-    // First enther the start funciton\r
+    // First enther the start function\r
     //\r
     FirstEnter = FALSE;\r
     //\r
@@ -697,23 +708,14 @@ TerminalDriverBindingStart (
     }\r
 \r
     //\r
-    // If RemainingDevicePath is NULL, then create default device path node\r
+    // If RemainingDevicePath is NULL, use default terminal type\r
     //\r
     if (RemainingDevicePath == NULL) {\r
-      DefaultNode = AllocateZeroPool (sizeof (VENDOR_DEVICE_PATH));\r
-      if (DefaultNode == NULL) {\r
-        Status = EFI_OUT_OF_RESOURCES;\r
-        goto Error;\r
-      }\r
-\r
       TerminalType = PcdGet8 (PcdDefaultTerminalType);\r
       //\r
-      // Must be between PCANSITYPE (0) and VTUTF8TYPE (3)\r
+      // Must be between PCANSITYPE (0) and TTYTERMTYPE (4)\r
       //\r
-      ASSERT (TerminalType <= VTUTF8TYPE);\r
-\r
-      CopyMem (&DefaultNode->Guid, gTerminalType[TerminalType], sizeof (EFI_GUID));\r
-      RemainingDevicePath = (EFI_DEVICE_PATH_PROTOCOL *) DefaultNode;\r
+      ASSERT (TerminalType <= TTYTERMTYPE);\r
     } else if (!IsDevicePathEnd (RemainingDevicePath)) {\r
       //\r
       // If RemainingDevicePath isn't the End of Device Path Node,\r
@@ -728,6 +730,8 @@ TerminalDriverBindingStart (
         TerminalType = VT100PLUSTYPE;\r
       } else if (CompareGuid (&Node->Guid, &gEfiVTUTF8Guid)) {\r
         TerminalType = VTUTF8TYPE;\r
+      } else if (CompareGuid (&Node->Guid, &gEfiTtyTermGuid)) {\r
+        TerminalType = TTYTERMTYPE;\r
       } else {\r
         goto Error;\r
       }\r
@@ -789,6 +793,10 @@ TerminalDriverBindingStart (
     if (TerminalDevice->EfiKeyFiFo == NULL) {\r
       goto Error;\r
     }\r
+    TerminalDevice->EfiKeyFiFoForNotify = AllocateZeroPool (sizeof (EFI_KEY_FIFO));\r
+    if (TerminalDevice->EfiKeyFiFoForNotify == NULL) {\r
+      goto Error;\r
+    }\r
 \r
     //\r
     // Set the timeout value of serial buffer for\r
@@ -926,6 +934,24 @@ TerminalDriverBindingStart (
         );\r
 \r
       break;\r
+\r
+    case TTYTERMTYPE:\r
+      AddUnicodeString2 (\r
+        "eng",\r
+        gTerminalComponentName.SupportedLanguages,\r
+        &TerminalDevice->ControllerNameTable,\r
+        (CHAR16 *)L"Tty Terminal Serial Console",\r
+        TRUE\r
+        );\r
+      AddUnicodeString2 (\r
+        "en",\r
+        gTerminalComponentName2.SupportedLanguages,\r
+        &TerminalDevice->ControllerNameTable,\r
+        (CHAR16 *)L"Tty Terminal Serial Console",\r
+        FALSE\r
+        );\r
+\r
+      break;\r
     }\r
 \r
     //\r
@@ -980,6 +1006,15 @@ TerminalDriverBindingStart (
                     );\r
     ASSERT_EFI_ERROR (Status);\r
 \r
+    Status = gBS->CreateEvent (\r
+                    EVT_NOTIFY_SIGNAL,\r
+                    TPL_CALLBACK,\r
+                    KeyNotifyProcessHandler,\r
+                    TerminalDevice,\r
+                    &TerminalDevice->KeyNotifyProcessEvent\r
+                    );\r
+    ASSERT_EFI_ERROR (Status);\r
+\r
     Status = gBS->InstallProtocolInterface (\r
                     &TerminalDevice->Handle,\r
                     &gEfiDevicePathProtocolGuid,\r
@@ -1151,9 +1186,6 @@ TerminalDriverBindingStart (
       goto Error;\r
     }\r
   }\r
-  if (DefaultNode != NULL) {\r
-    FreePool (DefaultNode);\r
-  }\r
 \r
   return EFI_SUCCESS;\r
 \r
@@ -1205,7 +1237,10 @@ Error:
       if (TerminalDevice->EfiKeyFiFo != NULL) {\r
         FreePool (TerminalDevice->EfiKeyFiFo);\r
       }\r
-\r
+      if (TerminalDevice->EfiKeyFiFoForNotify != NULL) {\r
+        FreePool (TerminalDevice->EfiKeyFiFoForNotify);\r
+      }\r
+  \r
       if (TerminalDevice->ControllerNameTable != NULL) {\r
         FreeUnicodeStringTable (TerminalDevice->ControllerNameTable);\r
       }\r
@@ -1222,10 +1257,6 @@ Error:
     }\r
   }\r
 \r
-  if (DefaultNode != NULL) {\r
-    FreePool (DefaultNode);\r
-  }\r
-\r
   This->Stop (This, Controller, 0, NULL);\r
 \r
   return Status;\r
@@ -1387,6 +1418,7 @@ TerminalDriverBindingStop (
         gBS->CloseEvent (TerminalDevice->TwoSecondTimeOut);\r
         gBS->CloseEvent (TerminalDevice->SimpleInput.WaitForKey);\r
         gBS->CloseEvent (TerminalDevice->SimpleInputEx.WaitForKeyEx);\r
+        gBS->CloseEvent (TerminalDevice->KeyNotifyProcessEvent);\r
         TerminalFreeNotifyList (&TerminalDevice->NotifyList);\r
         FreePool (TerminalDevice->DevicePath);\r
         if (TerminalDevice->TerminalConsoleModeData != NULL) {\r
@@ -1422,16 +1454,18 @@ TerminalUpdateConsoleDevVariable (
   )\r
 {\r
   EFI_STATUS                Status;\r
+  UINTN                     NameSize;\r
   UINTN                     VariableSize;\r
   UINT8                     TerminalType;\r
   EFI_DEVICE_PATH_PROTOCOL  *Variable;\r
   EFI_DEVICE_PATH_PROTOCOL  *NewVariable;\r
   EFI_DEVICE_PATH_PROTOCOL  *TempDevicePath;\r
+  EDKII_SET_VARIABLE_STATUS *SetVariableStatus;\r
 \r
   //\r
   // Get global variable and its size according to the name given.\r
   //\r
-  GetEfiGlobalVariable2 (VariableName, &Variable, NULL);\r
+  GetEfiGlobalVariable2 (VariableName, (VOID**)&Variable, NULL);\r
   if (Variable == NULL) {\r
     return;\r
   }\r
@@ -1439,9 +1473,10 @@ TerminalUpdateConsoleDevVariable (
   //\r
   // Append terminal device path onto the variable.\r
   //\r
-  for (TerminalType = PCANSITYPE; TerminalType <= VTUTF8TYPE; TerminalType++) {\r
+  for (TerminalType = PCANSITYPE; TerminalType <= TTYTERMTYPE; TerminalType++) {\r
     SetTerminalDevicePath (TerminalType, ParentDevicePath, &TempDevicePath);\r
     NewVariable = AppendDevicePathInstance (Variable, TempDevicePath);\r
+    ASSERT (NewVariable != NULL);\r
     if (Variable != NULL) {\r
       FreePool (Variable);\r
     }\r
@@ -1462,7 +1497,33 @@ TerminalUpdateConsoleDevVariable (
                   VariableSize,\r
                   Variable\r
                   );\r
-  ASSERT_EFI_ERROR (Status);\r
+\r
+  if (EFI_ERROR (Status)) {\r
+    NameSize = StrSize (VariableName);\r
+    SetVariableStatus = AllocatePool (sizeof (EDKII_SET_VARIABLE_STATUS) + NameSize + VariableSize);\r
+    if (SetVariableStatus != NULL) {\r
+      CopyGuid (&SetVariableStatus->Guid, &gEfiGlobalVariableGuid);\r
+      SetVariableStatus->NameSize   = NameSize;\r
+      SetVariableStatus->DataSize   = VariableSize;\r
+      SetVariableStatus->SetStatus  = Status;\r
+      SetVariableStatus->Attributes = EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS;\r
+      CopyMem (SetVariableStatus + 1,                          VariableName, NameSize);\r
+      CopyMem (((UINT8 *) (SetVariableStatus + 1)) + NameSize, Variable,     VariableSize);\r
+\r
+      REPORT_STATUS_CODE_EX (\r
+        EFI_ERROR_CODE,\r
+        PcdGet32 (PcdErrorCodeSetVariable),\r
+        0,\r
+        NULL,\r
+        &gEdkiiStatusCodeDataTypeVariableGuid,\r
+        SetVariableStatus,\r
+        sizeof (EDKII_SET_VARIABLE_STATUS) + NameSize + VariableSize\r
+        );\r
+\r
+      FreePool (SetVariableStatus);\r
+    }\r
+  }\r
+\r
   FreePool (Variable);\r
 \r
   return ;\r
@@ -1500,7 +1561,7 @@ TerminalRemoveConsoleDevVariable (
   //\r
   // Get global variable and its size according to the name given.\r
   //\r
-  GetEfiGlobalVariable2 (VariableName, &Variable, NULL);\r
+  GetEfiGlobalVariable2 (VariableName, (VOID**)&Variable, NULL);\r
   if (Variable == NULL) {\r
     return ;\r
   }\r
@@ -1525,7 +1586,7 @@ TerminalRemoveConsoleDevVariable (
     // Loop through all the terminal types that this driver supports\r
     //\r
     Match = FALSE;\r
-    for (TerminalType = PCANSITYPE; TerminalType <= VTUTF8TYPE; TerminalType++) {\r
+    for (TerminalType = PCANSITYPE; TerminalType <= TTYTERMTYPE; TerminalType++) {\r
 \r
       SetTerminalDevicePath (TerminalType, ParentDevicePath, &TempDevicePath);\r
 \r
@@ -1570,6 +1631,9 @@ TerminalRemoveConsoleDevVariable (
                     VariableSize,\r
                     NewVariable\r
                     );\r
+    //\r
+    // Shrinking variable with existing variable driver implementation shouldn't fail.\r
+    //\r
     ASSERT_EFI_ERROR (Status);\r
   }\r
 \r
@@ -1626,6 +1690,10 @@ SetTerminalDevicePath (
     CopyGuid (&Node.Guid, &gEfiVTUTF8Guid);\r
     break;\r
 \r
+  case TTYTERMTYPE:\r
+    CopyGuid (&Node.Guid, &gEfiTtyTermGuid);\r
+    break;\r
+\r
   default:\r
     return EFI_UNSUPPORTED;\r
   }\r